Comment l'architecture événementielle résout les défis des applications Web modernes

Bonjour, Habr!







Alors que nous poursuivons nos ventes pour les goûts les plus exigeants, nous tournons votre attention vers un autre thème de notre recherche créative: l'architecture événementielle (EDA). Sous la coupe, vous trouverez de magnifiques organigrammes et une histoire sur la façon dont ce paradigme innovant aide au développement d'applications Web.



Cet article examinera certains des défis qui stimulent l'innovation dans le développement Web moderne. Ensuite, nous plongerons dans l'architecture événementielle (EDA) pour relever ces défis en redéfinissant l'architecture des serveurs.



Les applications Web ont parcouru un long chemin depuis l'époque où le contenu HTML statique était diffusé à partir d'un serveur. Aujourd'hui, les applications Web sont devenues beaucoup plus complexes, elles utilisent une variété de cadres, de centres de données et de technologies. Au cours des dernières années, deux tendances peuvent être relevées qui déterminent le développement du marché informatique:



  • Transfert d'applications vers le cloud ;
  • Implémentation d'une architecture de microservices .


Ces idées déterminent en grande partie la façon dont les logiciels sont conçus et construits aujourd'hui. On peut dire qu'aujourd'hui nous ne construisons plus des applications, mais des plateformes. Les applications n'occupent plus d'espace informatique partagé. Au lieu de cela, ils doivent échanger des informations entre eux via des protocoles de communication légers tels que les API REST ou les appels de procédure à distance (RPC). Ce modèle a conduit à d'excellents produits tels que Facebook, Netflix, Uber, etc.

Cet article examinera certains des défis qui stimulent l'innovation dans le développement Web moderne. Ensuite, nous plongerons dans l'architecture événementielle (EDA), qui résout ces problèmes en redéfinissant l'architecture du serveur.



Problèmes actuels du web moderne



Toute technologie Web doit faire face aux défis que doivent relever les applications asynchrones multi-utilisateurs modernes, conçues pour fonctionner correctement:



Disponibilité



Désormais, nous ne travaillons pas avec une seule application, mais avec plusieurs - des dizaines, voire des centaines - de services associés, et chacun d'entre eux doit résoudre ses problèmes 24 heures sur 24, sept jours sur sept. Comment cela peut il etre accompli? Le plus souvent, le service est mis à l'échelle horizontalement vers plusieurs instances qui peuvent être réparties sur plusieurs centres de données pour garantir une haute disponibilité. Toutes les demandes pour ce service particulier sont acheminées et uniformément réparties sur toutes les instances. Certains outils de déploiement offrent des capacités d'auto-réparation, donc si une instance échoue, une autre est créée pour la remplacer.



Évolutivité



L'évolutivité s'apparente à bien des égards à la disponibilité. L'essence de l'accessibilité est de s'assurer qu'au moins une instance du service est opérationnelle, prête à répondre aux demandes entrantes. L'évolutivité, à son tour, est principalement liée aux performances. Si une application est surchargée, de nouvelles instances de cette application sont créées pour répondre au nombre accru de demandes. Mais la mise à l'échelle verticale des applications n'est pas une tâche triviale, en particulier lorsqu'il s'agit d'applications avec état .



Une source de vérité



Avant l'avènement des microservices, c'était une tâche assez simple. Toutes les données se trouvaient à un endroit, en règle générale, il s'agissait d'une ou d'une autre base de données relationnelle. Cependant, lorsque plusieurs services partagent une base de données, des problèmes tels que des dépendances entre différentes équipes concernant des changements de schéma ou des problèmes de performances peuvent être créés. Ce problème était généralement résolu en allouant sa propre base de données à chaque service. Une source de vérité distribuée est très utile pour maintenir une architecture propre, mais dans une telle situation, vous devez gérer des transactions distribuées et la complexité de la prise en charge de plusieurs bases de données.



Synchronicité



Dans un scénario de demande-réponse typique, le client attend que le serveur réponde; il bloque toutes les actions jusqu'à ce qu'il reçoive une réponse ou jusqu'à ce que le délai spécifié expire. Si vous prenez ce comportement et l'implémentez dans une architecture de microservice avec des chaînes d'appels qui traversent tout le système, vous pouvez facilement vous retrouver dans ce qu'on appelle «l'enfer des microservices». Tout commence par appeler un seul service, appelons-le "service A". Mais alors le service A doit appeler le service B, et le plaisir commence. Le problème avec ce comportement est le suivant: si le service lui-même est associé à des ressources bloquées (par exemple, un thread est suspendu), les délais augmentent de manière exponentielle. Si nous autorisons un délai de 500 ms par service et qu'il y a cinq appels de service dans la chaîne, le premier service aura besoin d'un délai de 2500 ms (2,5 secondes) et le dernier de 500 ms.







Les défis du web moderne



Introduction à l'architecture événementielle



L'architecture pilotée par les événements (EDA) est un paradigme d'architecture logicielle qui facilite la génération, la découverte, la consommation d'événements et leur réponse.




Dans les applications classiques à trois niveaux, le cœur du système est la base de données. Dans EDA, l'accent est mis sur les événements et la manière dont ils filtrent dans le système. Ce changement d'orientation nous permet de changer complètement la façon dont nous concevons les applications et résolvons les problèmes susmentionnés.



Avant de regarder exactement comment cela se fait dans EDA, regardons ce qu'est un «événement». Un événement est une action qui déclenche une notification ou une modification de l'état de l'application. La lumière s'est allumée (notification), le thermostat a éteint le système de chauffage (notification), l'utilisateur a changé son adresse (changement d'état), un de vos amis a changé son numéro de téléphone (changement d'état). Ce sont tous des événements, mais pas encore le fait que nous devrions les ajouter à la solution événementielle. On suppose que seuls les événements liés à l'entreprise sont ajoutés à l'architecture. L'événement «l'utilisateur passe une commande» est important d'un point de vue commercial, mais «l'utilisateur mange une pizza ou un déjeuner commandé» ne l'est pas.



Si vous pensez à certains événements, alors à certains, il est immédiatement clair qu'ils sont importants pour l'entreprise, et à certains - non. Surtout ceux qui se produisent en réponse à d'autres événements. Une technique appelée « assaut d'événement » est utilisée pour identifier les événements passant par le système . Les participants au développement d'applications (des programmeurs aux développeurs de logique métier et aux experts en la matière) sont convoqués et cartographient conjointement tous les processus métier, les présentant sous la forme d'événements spécifiques. Lorsqu'une telle carte est prête, le résultat du travail est formulé sous la forme d'exigences qui doivent être remplies lors du développement d'applications.







Un exemple de demande de réservation décrite par la méthode event assault



Après avoir identifié les événements qui nous intéressent et décidé comment les identifier, voyons comment ce paradigme peut résoudre les problèmes typiques mentionnés ci-dessus.



Le flux des événements est unidirectionnel: du producteur au consommateur. Comparez cette situation avec un appel REST. Le producteur d'événement n'attend en principe pas de réponse du consommateur, alors que dans le cas d'un appel REST, il y aura toujours une réponse. Aucune réponse signifie qu'il n'est pas nécessaire de bloquer l'exécution du code jusqu'à ce que quelque chose d'autre se produise. Dans ce cas, les événements deviennent de nature asynchrone , ce qui élimine complètement le risque de s'enliser dans les retards.



Les événements se produisent à la suite d'une action, il n'y a donc pas de système cible; on ne peut pas dire que le service A déclenche des événements sur le service B; mais nous pouvons dire que le service B s'intéresse aux événements générés par le service A. Certes, il peut y avoir d'autres "parties intéressées" dans ce système, par exemple les services C ou D.



Comment pouvons-nous nous assurer qu'un événement initié dans un certain système atteindra tous Des services «intéressés»? En règle générale, ces systèmes sont résolus à l'aide de courtiers de messages. Un courtier est simplement une application qui agit comme un intermédiaire entre l'émetteur d'événements (l'application qui a généré l'événement) et le consommateur d'événements. Ainsi, les applications peuvent être parfaitement détachées les unes des autres, prenant en charge le problème d' accessibilité, qui a été discuté ci-dessus dans ce post. Si l'application n'est pas disponible pour le moment, alors, de retour en ligne, elle commencera à consommer des événements et à les traiter, compensant tous les événements qui se sont produits pendant la période pendant laquelle elle n'était pas disponible.



Qu'en est-il de l'entrepôt de données? Les événements peuvent-ils être stockés dans une base de données ou est-ce que quelque chose d'autre est requis au lieu d'une base de données? Certes, les événements peuvent être stockés dans des bases de données, mais dans ce cas leur essence "événement" est perdue. Une fois qu'un événement s'est produit, nous ne pouvons plus le corriger, donc les événements sont essentiellement immuables. Les bases de données, à leur tour ... sont modifiables, après avoir entré les données dans la base de données, elles peuvent être modifiées.



Mieux vaut stocker les événements dans les journaux d' événements . Les journaux d'événements ne sont rien de plus que centralisésentrepôt de données, où chaque événement est enregistré sous la forme d'une séquence d'enregistrements immuables, le soi-disant «journal». Un journal peut être comparé à un journal, où chaque nouvel événement est ajouté à la fin de la liste. Vous pouvez toujours recréer l'état le plus récent en rejouant tous les événements du journal du début au présent.



Nous avons donc couvert tous les problèmes sauf l'évolutivité. Les services événementiels sont toujours conçus pour être déployés sur plusieurs instances. Étant donné que l'état en tant que tel est stocké dans le journal des événements, le service lui-même sera sans état, ce qui permet une mise à l'échelle chirurgicale précise de tout service d'intérêt.



La seule exception à ce principe concerne les services conçus pour créer des vues matérialisées.... En substance, une vue matérialisée est un état qui décrit un journal des événements à un moment donné. Cette approche est utilisée pour faciliter l'interrogation des données. Pour revenir à la question de la mise à l'échelle, une vue matérialisée est simplement une vue agrégée des événements, en forme de tableau; mais où stockons-nous ces tables? Le plus souvent, vous voyez de telles agrégations en mémoire, et en même temps, notre service se transforme automatiquement en un service avec état. Une solution simple et rapide consiste à fournir une base de données locale pour chaque service qui crée des vues matérialisées. De cette façon, l'état est stocké dans la base de données et le service s'exécute sans état.







Bien que l'architecture événementielle existe depuis plus de 15 ans, elle n'a gagné en popularité que récemment, et ce n'est pas un hasard. La plupart des entreprises traversent une étape de « transformation numérique » avec des demandes farouches. En raison de la complexité de ces exigences, les ingénieurs doivent maîtriser de nouvelles approches de la conception logicielle, impliquant notamment un affaiblissement du couplage des services entre eux et une réduction du coût de maintenance des services. L'EDA est une solution possible à ces problèmes, mais pas la seule. De plus, ne vous attendez pas à ce que tous les problèmes soient résolus, il vous suffit de passer à EDA. Certaines fonctionnalités peuvent encore nécessiter des API REST anciennes robustes ou le stockage d'informations dans une base de données. Choisissez celui qui vous convient le mieux et concevez-le correctement!



All Articles