web-dev-qa-db-fra.com

Quelles sont les différences entre un système de serveur basé sur des événements et basé sur des threads?

  • Node.js est une E/S pilotée par les événements et c'est un serveur à thread unique qui agit sur les rappels et ne bloque jamais le thread principal.

    1. Mais comment parvient-il à des E/S non bloquantes?
    2. s'il est facile à gérer, pourquoi le système basé sur les threads ne le gère-t-il pas?
    3. Ne fonctionne pas les autres threads (derrière un seul thread événementiel) comme basés sur des threads?
    4. si les autres threads signifient que les travailleurs (derrière le thread piloté par les événements) sont occupés, comment peut-il encore gérer les travaux sans bloquer?
  • basé sur les threads modèle affectant une tâche à un thread et s'il n'y a pas de thread inactif, bloquez les nouvelles tâches.

    1. si un thread peut gérer plusieurs tâches comme un thread unique événementiel qui gère toutes les E/S sans blocage, pourquoi le système basé sur les threads n'utilise pas cette tactique sur les threads occupés vers les E/S sans blocage.

Je me demande quelles sont les différences ( avantages/inconvénients ) entre les systèmes de serveurs événementiels et basés sur les threads.

26
erginduran

La différence pourrait être décrite comme suit (avec une certaine simplification):

  • dans les runtimes "pilotés par threads", lorsqu'une demande arrive, un nouveau thread est créé et toute la gestion est effectuée dans ce thread.

  • dans les runtimes "événementiels", lorsqu'une demande arrive, l'événement est distribué et le gestionnaire le récupère. Quand? Dans Node.js, il y a une "boucle d'événement" qui boucle essentiellement sur tous les morceaux de code qui doivent être exécutés et les exécute un par un. Le gestionnaire gérera donc l'événement une fois que la boucle d'événement l'a appelé. L'important ici est que tous les gestionnaires sont appelés dans le même thread - la boucle d'événements n'a pas de pool de threads à utiliser, elle n'a qu'un seul thread.

Dans un modèle "piloté par les événements", si un gestionnaire prend beaucoup de temps pour terminer (c'est-à-dire en ayant une boucle for intensive en calcul à l'intérieur), aucune autre requête ne sera traitée pendant ce temps, car la boucle d'événements n'invoquera pas le gestionnaire suivant avant la fin du gestionnaire actuel. Ce n'est généralement pas un problème en raison de la nature asynchrone de Javascript.

D'un autre côté, dans le modèle "piloté par threads", si le gestionnaire prend beaucoup de temps à terminer, cela ne nuira pas beaucoup aux autres threads, car ils peuvent s'exécuter en même temps indépendamment.

Malheureusement, la création d'un nouveau thread ajoute une surcharge et si vous devez gérer des milliers de connexions simultanées, cela peut devenir un fardeau. C'est pourquoi Node.js est considéré comme rapide - peu importe le nombre de connexions que vous gérez, il n'y a qu'un seul thread 1 . Vous devez juste être un peu prudent pour ne bloquer aucun des gestionnaires afin de faire avancer les choses. Heureusement, la plupart du temps, il n'est pas si facile d'écrire du code JavaScript bloquant.

Il est également important de noter que l'écriture de code asynchrone est possible dans la plupart des runtimes. Cependant, il est devenu le plus largement utilisé dans Node.js, en raison de la nature de Javascript. Grâce à cela, pratiquement toutes les bibliothèques que vous utilisez dans Node seront asynchrones.

Voir cet article (et photos) pour une explication de la boucle d'événement.

1 Bien sûr, il y a plus d'un thread dans le processus Node.js, certains d'entre eux sont liés aux E/S. Mais la logique de votre application est gérée dans un seul thread.

36
kamituel