12
votes

Blocage IO / Ruby sur rails

Je contemplerai d'écrire une application Web avec des rails. Chaque demande effectuée par l'utilisateur dépendra d'une API externe appelée. Cette API externe peut être au hasard très lente (2-3 secondes), et donc évidemment, cela affecterait une demande individuelle.

Pendant ce temps, lorsque le code attend que l'API externe revienne, les demandes d'utilisateurs supplémentaires seront-elles bloquées?

Juste pour plus de clarification, car il semble y avoir une certaine confusion, c'est le modèle que je prévois:

  1. Alice apporte la demande à mon application Web. Pour remplir cela, un appel à API Server A est effectué. Le serveur API A est lent et prend 3 secondes à compléter.
  2. Pendant ce temps d'attente lorsque l'application Rails appelle API Server A, BOB fait une demande qui doit apporter une demande à API Server b.

    est l'interpréteur Ruby (1.9.3) (ou quelque chose dans le cadre de Rails 3.x) pour bloquer la demande de Bob, ce qui lui nécessite d'attendre la demande d'Alice?


2 commentaires

J'ai une question similaire..mais que je me demandais simplement, faites-vous des requêtes de DB de votre application Rails via Aciverecord, ou les données sont purement entraînées à partir du serveur API Backend qui rendent la requête DB et renvoient le résultat à vos rails finir?


@Bennytjia les deux. Une demande individuelle utilisera à la fois des données stockées localement et des données uniques renvoyées par le serveur API.


3 Réponses :


0
votes

Très probablement, oui. Il y a des façons autour de cela, évidemment, mais aucun d'entre eux n'est facile.

La meilleure question est, pourquoi avez-vous besoin de frapper l'API externe sur chaque demande? Pourquoi ne pas mettre en place une couche de cache entre votre application Rails et l'API externe et utilisez-le pour la majorité des demandes?

De cette façon, avec une logique personnalisée pour expirer le cache, vous aurez une application Snappy Rails et pour pouvoir tirer parti du service d'API externe.


3 commentaires

Les données retournées changent avec chaque demande. La mise en cache n'est donc pas possible.


Alors, ce que vous dites, c'est votre API est votre base de données? Cela ne semble pas réalisable à long terme ...


L'API n'agit pas comme une base de données.



8
votes

Si vous utilisez uniquement un serveur à filetage unique, non éventué (ou n'utilisez pas d'E / S éventuellement avec un serveur événementiel), oui. Parmi les autres solutions utilisant mince et em-synchrony évitera ceci.

Elaborer, basé sur votre mise à jour:

Non, ni Ruby ni rails ne vont causer à bloquer votre application. Vous avez laissé la partie qui sera, bien que: le serveur Web. Vous avez besoin de plusieurs processus, de threads multiples ou d'un serveur événementiel associé à vos demandes de service Web avec une bibliothèque d'E / S éventuellement.

@alexd décrit en utilisant plusieurs processus. Personnellement, je privilégie un serveur éventuel car je n'ai pas besoin de savoir / deviner à l'avance combien de demandes simultanées, je pourrais avoir (ou utiliser quelque chose qui couvre des processus basés sur la charge.) Un seul nginx Processus en frontage d'un seul Thin Processus de serveur de demandes parallèles.


2 commentaires

réseau la latence? Si vous voulez dire que l'utilisateur actuel sera obligé d'attendre, bien sûr, ils le feront (mais je suppose de la manière dont il a écrit la question, c'est inévitable). Je lis la question de ne pas éviter la latence pour l'utilisateur frappant le service externe, mais à propos de bloquer d'autres demandes simultanées.


@smparkes J'ai ajouté des éclaircissements supplémentaires à la question concernant cette question concernant



3
votes

La réponse à votre question dépend du serveur que votre application Rails est activée. Qu'est-ce que tu utilises maintenant? Mince? Licorne? Apache + passager?

Je recommande de tout coeur Licorne pour votre situation - il est très facile d'exécuter plusieurs processus de serveur en parallèle et vous pouvez configurer le nombre de processus parallèles simplement en modifiant un numéro dans un fichier de configuration. Alors qu'un ouvrier de la licorne gère la demande de haute latence d'Alice, un autre ouvrier de la licorne peut utiliser vos cycles de processeurs gratuits pour gérer la demande de Bob.


0 commentaires