Cet article s’insère dans notre série « Chaos Engineering ».

Le contexte

Les architectures applicatives actuelles s’éloignent de plus en plus d’une structure en blocs monolithiques, pour s’orienter vers des architectures basées sur de la composition de services et structurées en systèmes distribués, notamment par l’utilisation des micro-services.

Les applications basées sur ces architectures proposent des fonctionnalités provenant de l’interaction de leurs composants, et de la bonne collaboration de l’ensemble des composants.

Les composants de ces architectures peuvent se compter par centaines, ce qui apporte des problématiques de gestion applicatives de plus en plus liées aux systèmes distribués, et acquièrent des propriétés similaires à celles des systèmes complexes.

Un système complexe peut être défini de plusieurs façons d’après le prisme dont il est observé, nous considèrerons les quelques propriétés essentielles suivantes, utiles pour la suite:

  • il est composé d’un grand nombre d’éléments en interaction et ce, de manière simultanée
  • le comportement d’un système complexe est très difficile à modéliser, même en connaissant parfaitement chaque élément de ce système. Le comportement est émergent, car il est issu des différentes interactions entre les éléments le composant.
  • l’action d’un composant peut avoir un effet sur son propre état, sur l’état d’autres composants et sur l’état global du système par propagation
  • la connaissance d’une partie du système ne permet pas de déterminer l’état global du système

Les fonctionnalités proposées par une application sur l’interaction de composants à l’intérieur d’un système complexe seront donc systémiques, et dépendantes du bon fonctionnement et de la bonne coordination des différents composants.

Malheureusement, la moindre faille peut avoir des conséquences lourdes sur la bonne fonctionnalité de ces systèmes (voir propriétés ci-dessus), et il est très difficile, voire impossible de modéliser l’ensemble des conséquences pouvant émerger de la faille d’un composant (failles en cascade, goulot d’étranglement) et/ou de l’orchestration de différents composants (« retry storms »).

Les tests existants (unitaires, intégration, techniques) permettent de tester la bonne fonctionnalité de composants isolés, ou en intégration simple, mais restent très limités dans la possibilité de tester la robustesse d’un système complexe à l’échelle réelle car ils restent déterministes.

Utiliser un environnement autre que l’environnement réel peut aussi entraîner des biais qui fausseront les observations et la possibilité de les transposer dans la réalité.

On pré-supposera finalement que le fait d’observer le système réel n’a pas d’impact conséquent sur le comportement de ce système.

Qu’est-ce que le chaos engineering?

Le chaos engineering est une approche mise en avant par Netflix en 2008, afin d’augmenter sa confiance en sa capacité de fournir des flux vidéos et services associés à des millions de personnes à partir d’une architecture distribuée complexe et hébergée dans un cloud public.

Le chaos engineering adopte une approche proactive d’expérimentation au niveau de l’environnement de production, afin de détecter les faiblesses d’un système, en utilisant une méthodologie proche de l’étude des systèmes dynamiques par simulation. On va donc étudier la résilience du système et sa capacité à s’adapter à différents problèmes.

Dans l’étude des systèmes dynamiques, comme par exemple dans les simulations multi-agents dynamiques à grande échelle [2], la méthodologie est la suivante :

  1. Définition des variables d’observation saillantes du système, permettant de mesurer ses performances ou l’état « normal » de fonctionnement. Comme éléments de mesure, des variables d’observation liées aux propriétés du système que nous voulons tester (temps de réponse, ..) sont utilisées.
  2. Identification de l’état stable (fonctionnellement adéquat) du système, sur une période donnée, qui correspond à son comportement dit « normal ». Cette notion d’état stable peut être une agrégation de plusieurs phases d’observation dans les mêmes conditions initiales de départ et sur la même durée, afin d’atténuer les bruits ponctuels.
  3. Identifier les perturbations au niveau des composants ou du système distribué pouvant entraîner l’échec des fonctionnalités (panne de composant, rupture des communications inter-composants, etc..), issus d’évènements réels observés, qui constitueront autant de moyens d’expérimentations.
  4. Avec les mêmes conditions initiales que pour l’identification de l’état stable, introduire un « choc » lié à une perturbation ou faute identifiée à un instant t et observer les conséquences par rapport au comportement du système dans son état stable.

On se focalisera donc sur la notion d’observation du comportement au niveau de la fonctionnalité nominale (état stable) et les divergences observées lors de l’introduction des chocs au niveau systémique (« controlled failure-injection »).

L’hypothèse de base est que le système gardera un état proche de l’état stable malgré l’introduction des chocs. Si cette hypothèse est vérifiée, alors on peut avoir confiance dans la robustesse du système. Si elle ne l’est pas, alors le système souffre de fragilités qu’il sera nécessaire d’identifier et de prendre en compte.

Certaines précautions de bon sens sont quand même à garder à l’esprit et le choix des chocs à injecter en environnement de production fait partie intégrante de la responsabilité du chaos engineer, vu que ces chocs peuvent créer des pannes graves sur le système et le service fourni.

Introduire les chocs : les chaos monkeys

L’introduction de chocs et l’analyse des conséquences étant une tâche non triviale, le chaos engineering met aussi en avant l’automatisation de ces tâches par des agents du chaos aussi appelés les « chaos monkeys ».

Un chaos monkey est une interface, derrière laquelle seront implémentés les comportements associés aux chocs voulus, et qui seront appliqués aux périodes ou intervalles sélectionnés. Netflix fournit sur github une implémentation disponible dans les références de cet article [3].

Un chaos monkey permettra par exemple de tuer un processus associé à un micro-service, ou l’ajout d’un blocage sur un firewall entraînant une disruption des interactions lors de l’orchestration de services.

Au fur et à mesure des expérimentations, l’équipe en charge du chaos engineering pourra disposer d’un ensemble de monkeys (ou simian army par Netflix) qui permettront de vérifier les différents aspects de résilience du système.

Autour du chaos engineering

Le chaos engineering n’est pas une démarche isolée et s’inscrit dans la collaboration (DevOps) des équipes de développement et des opérationnels qui disposent de points de vue complémentaires sur la compréhension des comportements systémiques. Ces équipes se concertent pour identifier les causes de disruption et identifier les chaos monkeys à mettre en place lors des phases d’expérimentation.

Un point intéressant remonté par B. Gakic lors de la présentation Devoxx 2018 [1][4], est que ces équipes font aussi partie intégrante du système complexe. Les expérimentations chaos engineering permettent aussi d’identifier les faiblesses au niveau des équipes par rapport à leur maîtrise lors des remontées de pannes en production.

Afin de se concerter et permettre aux équipes de s’exercer, le concept de « GameDay » (ou drills/randori d’après votre méthodologie/discipline sportive préférée) a été introduit par Netflix et repris par les équipes de Oui-Sncf [5] en introduisant de la gamification. Cela a permis aux équipes de renforcer leur cohésion et leur compréhension.

Références

Ci-dessous quelques références pour mieux se documenter :

Références article

 

Vous avez aimé cet article ? Découvrez ou redécouvrez l’autre épisode de la série « Chaos Engineering » :