J'ai beaucoup lu sur les architectures de microservices pour les applications serveur et je me suis demandé pourquoi l'utilisation du réseau interne n'était pas un goulot d'étranglement ni un inconvénient majeur par rapport à une architecture monolithique.
Par souci de précision, voici mes interprétations des deux termes:
Architecture monolithique: une application dans une seule langue qui gère l’ensemble des fonctionnalités, des données, etc. Un équilibreur de charge distribue les demandes de l’utilisateur final sur plusieurs machines, chacune exécutant une instance de notre application.
Architecture de microservice : de nombreuses applications (microservices) gèrent une petite partie des fonctionnalités et des données. Chaque microservice expose une API commune accessible via le réseau (par opposition à une communication interprocessus ou à une mémoire partagée sur le même ordinateur). Les appels d'API sont généralement stichés sur le serveur pour produire une page, bien qu'une partie de ce travail soit effectuée par le client interrogeant des microservices individuels.
À mon imagination naïve, il semble qu'une architecture de microservices utilise un trafic réseau lent par opposition à des ressources plus rapides sur le même ordinateur (la mémoire et le disque). Comment s'assurer que les requêtes d'API via le réseau interne ne ralentiront pas le temps de réponse global?
la source
Réponses:
Les réseaux internes utilisent souvent des connexions 1 Gbit / s ou plus rapides. Les connexions ou liaisons par fibres optiques permettent des largeurs de bande beaucoup plus élevées entre les serveurs. Imaginez maintenant la taille moyenne d'une réponse JSON d'une API. Combien de ces réponses peuvent être transmises sur une connexion de 1 Gbps en une seconde?
Faisons le calcul. 1 Gbps est de 131 072 Ko par seconde. Si une réponse JSON moyenne est de 5 Ko (ce qui est assez!), Vous pouvez envoyer 26 214 réponses par seconde de bout en bout avec seulement une paire de machines . Pas si mal, n'est ce pas?
C'est pourquoi la connexion réseau n'est généralement pas le goulot d'étranglement.
Un autre aspect des microservices est que vous pouvez facilement évoluer. Imaginez deux serveurs, l'un hébergeant l'API, l'autre le consommant. Si jamais la connexion devient un goulot d'étranglement, ajoutez simplement deux autres serveurs et vous pourrez doubler les performances.
C’est à ce moment-là que nos 26 214 réponses précédentes par seconde deviennent trop petites pour l’ampleur de l’application. Vous ajoutez neuf autres paires et vous pouvez maintenant servir 262 140 réponses.
Mais revenons à notre paire de serveurs et faisons des comparaisons.
Si une requête moyenne non mise en cache sur une base de données prend 10 ms, vous êtes limité à 100 requêtes par seconde. 100 requêtes. 26 214 réponses. Atteindre la vitesse de 26 214 réponses par seconde nécessite une grande quantité de mise en cache et d’optimisation (si la réponse doit réellement faire quelque chose d’utile, comme interroger une base de données; les réponses de style "Hello World" ne sont pas admissibles).
Sur mon ordinateur, à l'heure actuelle, la page d'accueil de DOMContentLoaded pour Google s'est produite à 394 ms. après l'envoi de la demande. C'est moins de 3 demandes par seconde. Pour la page d’accueil de Programmers.SE, cela s’est passé à 603 ms. après l'envoi de la demande. Ce n'est même pas 2 demandes par seconde. Au fait, j'ai une connexion Internet à 100 Mbps et un ordinateur rapide: beaucoup d'utilisateurs vont attendre plus longtemps.
Si le goulot d'étranglement est la vitesse du réseau entre les serveurs, ces deux sites pourraient littéralement faire des milliers d'appels vers différentes API tout en servant la page.
Ces deux cas montrent que le réseau ne sera probablement pas votre goulot d'étranglement en théorie (en pratique, vous devez effectuer les tests de performances et le profilage réels pour déterminer l'emplacement exact du goulot d'étranglement de votre système hébergé sur un matériel particulier). Le temps consacré au travail réel (qu'il s'agisse de requêtes SQL, de compression, etc.) et l'envoi du résultat à l'utilisateur final sont beaucoup plus importants.
Pensez aux bases de données
Généralement, les bases de données sont hébergées séparément de l'application Web qui les utilise. Cela peut poser un problème: qu'en est-il de la vitesse de connexion entre le serveur hébergeant l'application et le serveur hébergeant la base de données?
Il semble que dans certains cas, la vitesse de connexion pose problème, c’est-à-dire lorsque vous stockez d’énormes quantités de données qui n’ont pas besoin d’être traitées par la base de données elle-même et qui devraient être disponibles maintenant (c’est-à-dire de gros fichiers binaires). Mais de telles situations sont rares: dans la plupart des cas, la vitesse de transfert n’est pas si grande comparée à la vitesse de traitement de la requête elle-même.
Lorsque la vitesse de transfert est réellement importante, c'est lorsqu'une entreprise héberge de grands ensembles de données sur un NAS et que plusieurs clients accèdent au NAS en même temps. C'est là qu'un SAN peut être une solution. Ceci étant dit, ce n'est pas la seule solution. Les câbles Cat 6 peuvent supporter des vitesses allant jusqu'à 10 Gbps; La liaison peut également être utilisée pour augmenter la vitesse sans changer les câbles ou les adaptateurs réseau. D'autres solutions existent, impliquant la réplication de données sur plusieurs NAS.
Oubliez la vitesse; penser à l'évolutivité
Un point important d'une application Web est de pouvoir évoluer. Bien que les performances réelles importent (car personne ne veut payer pour des serveurs plus puissants), l’évolutivité est beaucoup plus importante, car elle vous permet de lancer du matériel supplémentaire en cas de besoin.
Si vous avez une application pas particulièrement rapide, vous perdrez de l'argent car vous aurez besoin de serveurs plus puissants.
Si vous avez une application rapide qui ne peut pas évoluer, vous perdrez des clients car vous ne serez pas en mesure de répondre à une demande croissante.
De la même manière, les machines virtuelles étaient perçues il y a une décennie comme un énorme problème de performances. En effet, héberger une application sur un serveur ou sur une machine virtuelle avait un impact important sur les performances. Bien que l'écart soit beaucoup plus petit aujourd'hui, il existe toujours.
Malgré cette perte de performances, les environnements virtuels sont devenus très populaires en raison de la flexibilité qu’ils offrent.
Comme avec la vitesse du réseau, vous constaterez peut-être que la VM est le goulet d'étranglement réel et que, compte tenu de votre taille réelle, vous économiserez des milliards de dollars en hébergeant votre application directement, sans les VM. Mais ce n'est pas ce qui se passe pour 99,9% des applications: leur goulot d'étranglement est ailleurs et l'inconvénient d'une perte de quelques microsecondes à cause de la VM est facilement compensé par les avantages de l'abstraction matérielle et de son évolutivité.
la source
Je pense que vous lisez trop dans la partie "micro". Cela ne signifie pas que chaque classe doit être remplacée par un service réseau, mais une application monolithique doit être divisée en composants de taille raisonnable, chacun traitant d'un aspect de votre programme. Les services ne se parlent pas, vous pouvez donc, au pire, diviser une requête réseau volumineuse en plusieurs requêtes plus petites. Les données renvoyées ne seront de toute façon pas très différentes de celles que vous recevrez (bien que vous puissiez renvoyer plus de données et les consolider dans le client)
la source
En structurant votre accès au code et aux ressources de manière à ce que le système résultant puisse être suffisamment souple pour être exécuté en tant qu’application monolithique ou distribuée via une configuration. Si vous éliminez le mécanisme de communication derrière une interface commune et que vous construisez votre système en gardant à l'esprit la simultanéité, vous pouvez facilement tout optimiser après avoir profilé votre système et trouvé les véritables goulots d'étranglement.
la source
J'aimerais ajouter un point de vue différent, issu d'un secteur différent avec des hypothèses très différentes: la simulation distribuée (au niveau de l'entité). Conceptuellement, cela ressemble beaucoup à un jeu vidéo FPS distribué. Principales différences: tous les joueurs partagent un certain état: où se trouve le dragon actuellement; pas d'appels de base de données; tout est maintenu en RAM pour la vitesse et la faible latence, le débit est moins pertinent (mais je suppose que vous ne pouvez pas l'ignorer complètement non plus).
Vous pouvez considérer chaque application participante comme un monolithe (représentant toutes les facettes d’un joueur) ou comme un microservice (représentant un seul joueur dans une foule).
Mes collègues se sont montrés intéressés à décomposer une seule application participante proprement dite, davantage en microservices plus petits qui pourraient être partagés, par exemple un arbitrage de dommages ou des calculs de ligne de mire, des éléments qui sont généralement intégrés aux simulations.
Le problème est la latence de la distribution des appels et de l'attente des demandes. La bande passante est sans importance et abondante de toute façon, comme d'autres l'ont souligné. Mais si un calcul en visibilité directe passe de 1 microsec à 100 microsecondes (par exemple, en raison de la file d'attente dans le nouveau microservice partagé entre toutes les applications du lecteur), la perte est énorme (il faudra peut-être plusieurs calculs chaque mise à jour, plusieurs mises à jour / seconde).
Réfléchissez très attentivement au fonctionnement des services, à leur appel et aux données échangées. Nos applications n'échangent déjà pas que des informations de position, elles échangent des informations de comptabilisation mortes - je suis à la position x, dans la direction y à la vitesse q. Et je n'ai pas à mettre à jour mes informations jusqu'à ce que ces hypothèses changent. Beaucoup moins de mises à jour et de latence (tout en posant un problème) sont proportionnellement moins fréquentes.
Donc, plutôt que de demander un service avec un grain fin à une fréquence plus élevée, essayez de réduire la fréquence en:
Rappelez-vous maintenant de vérifier vos hypothèses sur votre système. Si vous êtes plus préoccupé par le débit que par le temps de latence, ou si vous n'avez pas d'état partagé, etc., utilisez bien sûr les microservices là où ils ont un sens. Je dis juste peut-être que ne les utilisez pas là où ils n’ont pas de sens.
la source
Votre imagination naïve a raison. Et souvent, cela n'a pas d'importance. Les machines modernes sont rapides. Les principaux avantages de l’architecture de micro-services se traduisent par des efforts et des délais de développement et de maintenance.
Et bien sûr, il n’existe aucune règle interdisant l’utilisation de la mémoire partagée ou le déploiement physique de plusieurs services dans un seul exécutable. Tant que vous le concevez pour ne pas dépendre de cela.
la source
Comme beaucoup de gens l'ont mentionné, il ne s'agit pas de goulots d'étranglement du réseau. C'est plus une question de fragilité du réseau. La première étape consiste donc à éviter les communications synchrones. C'est plus facile que ça en a l'air. Tout ce dont vous avez besoin, c'est des services avec de bonnes limites. Des frontières justes font que les services sont autonomes, faiblement couplés et très cohérents. Un bon service n'a pas besoin d'informations d'un autre service, il les a déjà. Les bons services ne peuvent communiquer que par des événements. Les bons services finissent également par être cohérents, il n'y a donc pas de transactions distribuées.
Pour parvenir à ce résultat, vous devez d'abord identifier les capacités de votre entreprise. La capacité métier est une responsabilité métier spécifique. Une certaine contribution à la valeur commerciale globale. Voici donc ma séquence de pas que je fais en pensant aux limites du système:
N'oubliez pas que les services métier incluent les personnes, les applications et les processus métier. Habituellement, seule une partie de celle-ci est représentée en tant qu'autorité technique.
Cela peut sembler un peu abstrait, un exemple d’identification des limites de service serait probablement intéressant.
la source
Juste un autre facteur à ajouter aux réponses actuelles. Avec des services à grain grossier . Vous voulez éviter la latence de tous les appels. Ainsi, au lieu de faire 10 appels, vous effectuez un appel qui obtient 10 éléments de données nécessaires à un DTO.
Et rappelez-vous que les microservices ne sont pas aussi micro que les gens le pensent.
la source