Académique Documents
Professionnel Documents
Culture Documents
INFORMATIQUE
Migration des briques de bases du SI
Olivier PICARD
34002455
M2 Informatique
Je tiens à remercier toute l’équipe pour son accueil chaleureux et leur constante bonne humeur.
J’aimerais tout particulièrement remercier mon tuteur Jepthé CLAIN pour sa disponibilité à mon égard,
ses nombreux et judicieux conseils, et aussi de m’avoir donné la possibilité et le temps nécessaire à l’ap-
prentissage et à l’assimilation de toutes les connaissances acquises durant ce stage.
Je remercie également Mamy Haja Rakotobe pour les discussions enrichissantes qui m’ont permis d’avoir
une vision différente du monde du travail.
Olivier Picard
2 Introduction 5
4 Contexte du stage 6
4.1 Maintenance applicative . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 7
4.2 Maintenance du système d’exploitation . . . . . . . . . . . . . . . . . . . . . . . . . . . 7
4.2.1 Pannes matérielles . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 7
4.3 Objectifs . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 8
5 Sujet de stage 8
7 MOOC et apprentissage 12
7.1 Méthodologie d’apprentissage . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 12
7.2 Description des compétences acquises . . . . . . . . . . . . . . . . . . . . . . . . . . . . 13
7.2.1 Docker . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 13
7.2.2 Docker Compose . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 14
10 KeepAlived 17
10.1 Fonctionnement théorique et recherches . . . . . . . . . . . . . . . . . . . . . . . . . . . 17
10.2 Mise en pratique . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 20
10.3 Démarrage sur une IP fixe . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 21
10.4 Bind sur une adresse qui n’existe pas . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 21
15 Traefik 32
15.1 Définition . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 32
15.2 Pourquoi un reverse proxy ? . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 32
15.3 Rapide état de l’art . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 33
15.4 Les avantages de Traefik . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 34
15.5 Pourquoi choisir Traefik . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 34
15.6 Difficultés . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 34
16 ProxySQL 35
16.1 Fonctionnalités . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 35
16.2 Rapide état de l’art . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 35
17 Replication Manager 36
17.1 Mission . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 36
17.2 Sharding Mysql . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 36
17.3 Le choix de l’architecture . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 37
17.3.1 Pourquoi avoir un cluster de trois machines . . . . . . . . . . . . . . . . . . . . . 37
17.3.2 Pourquoi avoir un seul maı̂tre sur le cluster . . . . . . . . . . . . . . . . . . . . . 37
17.4 Pourquoi utiliser replication manager . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 39
17.5 Difficultés . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 39
19 Conclusion 41
20 Annexes techniques 42
20.1 Annexe A : mise en place de Docker et Docker Compose . . . . . . . . . . . . . . . . . . 42
20.1.1 Annexe B : déploiement manuel sur hôte distant - Configuration . . . . . . . . . . 44
20.2 Annexe C : configuration d’un DNS avec bind9 . . . . . . . . . . . . . . . . . . . . . . . 45
20.3 Annexe D : création d’un registry . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 46
Dans le cadre d’un projet visant à améliorer la structure existante de la DSI[1], le travail qui m’a été demandé est la
migration des bases du SI. Cette migration concerne en particulier le transfert des bases de données MariaDB[2] sur des
serveurs hautes disponibilités pour l’Université[3] de la Réunion. Le document fait également état des tâches réalisées
et de mes recherches sur le fonctionnement des outils dans le domaine du réseau, de la DevOps[4] mais aussi sur le
système Linux/Debian[5].
As part of a project to improve the existing structure of the DSI, my work is about migration of Information System(SI)
bases. This migration focus precisely on MariaDB database transfert to high availability servers for ’Univeristé de la
Réunion’. This document also describe my tasks achieved and my reseaches. The higlight is put on the network, De-
vOps and also on Linux/Debian.
Mots-clefs : Réseaux, Docker, Serveurs hautes disponibilités, CAS, Docker Swarm, Traefik
2 Introduction
Ce rapport a pour vocation de présenter le stage de six mois que j’effectue durant ma dernière année de
Master 2 à l’Université de la Réunion. j’ai choisi ce stage car il m’a permis de découvrir des domaines et
outils que je ne connaissais que très peu, comme la conteneurisation. De plus ce stage m’a offert la pos-
sibilité d’accéder à des services en fonctionnement non interrompus utilisés par des milliers d’utilisateurs.
Grâce à cela, j’ai pu comprendre les difficultés et les rouages essentiels au bon fonctionnement d’un tel
système. Cette expérience en milieu professionnel m’a permis de prendre en main de nouveaux outils, et
d’acquérir une méthode de travail utile pour la suite de mon parcours.
Ce rapport fait aussi état des compétences théoriques que j’ai pu mettre en pratique, des missions qui
m’ont été confiées, ainsi que la rigueur acquise au sein de la Direction des Systèmes d’Informations (DSI)
de l’Université de la Réunion.
sont grandement facilitées. Il se trouve que les points de blocage sont plus rapidement résolus. Toutefois
la proximité présente aussi quelques inconvénients, tels que les bruits et les déplacements qui diminuent la
productivité. Heureusement que la bonne humeur qui y règne gomme totalement les défauts qu’imposent le
travail en open space.
Dans le contexte particulier du confinement qu’impose le COVID19, J’ai été autorisé à télétravailler. Tra-
vailler à son domicile présente de très nombreux avantages. Notamment, il est beaucoup plus facile de
s’approprier le projet, et de le considérer comme un projet personnel. Ainsi la motivation et la productivité
sont accrues.
4 Contexte du stage
Mon stage se porte sur le DevOps et s’intègre au sein de la volonté de la DSI d’améliorer la disponibilité
des services proposés. En quelques mots, mon travail vise à rendre certaines applications plus résistantes à
la fois aux pannes et aux fortes affluences.
Maintenir des serveurs qui offrent un accès à l’intégralité des membres de l’Université de la Réunion est
une tâche complexe. Les applications proposées doivent être accessibles 24h/24 et 7j/7. On peut prendre
l’exemple de l’emploi du temps. Il n’est absolument pas envisageable d’arrêter ce service, pour la simple rai-
son qu’il est utilisé aussi bien pendant et en dehors des heures d’ouverture de l’université. Il existe d’autres
services comme Moodle qui sont plus sensibles et doivent être hautement disponibles, afin d’assurer une
fonctionnalité permettant la remise des travaux aux enseignants et l’accès aux cours. Les serveurs sont ainsi
très sollicités. Par conséquent, il est très difficile de les maintenir en assurant les mises à jour à la fois du
système d’exploitation, et de l’ensemble des applications. D’un regard extérieur, il est très probable qu’on
ne puisse percevoir la difficulté à faire des mises à jour au niveau applicatif. Mais je propose que l’on se
penche un peu plus sur ce sujet.
Supposons que l’on dispose d’une application programmée en Java et d’un serveur Tomcat. Cette appli-
cation a été développée il y a de cela quelques années. Au fil du temps, des mises à jour majeures ont été
publiées par Tomcat. En théorie on change de version de Tomcat en se mettant sur la plus récente stable et
supportée pour le long terme. Mais dans les faits, c’est un peu différent. Changer de version signifie arrêter
tous les services liés au serveur Tomcat. Arrêter un service utilisé par des milliers d’individus n’est pas
particulièrement opportun, ce qui peut éventuellement impacter de nombreux utilisateurs. De plus, selon
la maintenance à effectuer, cela s’avère très chronophage et nécessiterait le redémarrage de l’ensemble des
services, et de nombreuses interventions manuelles qui ont été définies il y a quelques années, lors de la
création du service. Ces manipulations peuvent être des sources d’erreurs et d’oublis. Mon rôle durant ce
stage est d’intervenir pour ”conteneuriser” les applications afin de les rendre plus facilement maintenables.
Je reviendrais plus en détail sur ce qu’est la conteneurisation.
Cette partie est étroitement liée à celle qui décrit les difficultés de la ”maintenance applicative”. Mais les
conséquences d’une maintenance du système d’exploitation peut entraı̂ner des problèmes de compatibilité
avec les applications existantes. On peut citer l’obligation d’utiliser les dernières technologies de transmis-
sions sécurisées. L’utilisation des derniers protocoles de sécurités permet en effet de mieux protéger les
services, mais sont aussi sources de bugs qui peuvent s’avérer difficiles à résoudre. Si de nombreux services
sont dépendants d’une version spécifique de ce protocole (par exemple TLS), il peut être délicat de passer à
une version plus récente. Ces opérations s’avèrent être très chronophages et peuvent causer des erreurs. Une
maintenance du système d’exploitation peut éventuellement affecter un ensemble conséquent de services,
et peut même les rendre inopérants.
4.3 Objectifs
Comme on a pu le voir précédemment, mettre des applications ou un système à jour est une tâche
délicate qui peut compromettre la stabilité du système. Les dépendances des applications sont difficiles
à faire évoluer, et nécessitent souvent quelques modifications du code source de l’application. Pour cela, on
doit prendre en considération les changements apportés par les nouvelles versions. Les pannes matérielles
peuvent devenir problématiques, et mettre en péril une grande partie des services.
5 Sujet de stage
Après une vue d’ensemble des problèmes rencontrés et des objectifs de la DSI, j’aborderais mon su-
jet de stage qui se porte sur le DevOps. J’ai pour mission de migrer des services principaux du système
d’information vers un cluster haute disponibilité, et d’intervenir dans l’optique d’améliorer la stabilité et
la maintenance des services fournis par la DSI. Le stage s’étalant sur une période de six mois, je ne peux
migrer l’ensemble des services. L’objectif principal à été de me concentrer sur la base de données MariaDB.
Cette dernière constitue un besoin grandissant pour la DSI.
Un cluster hautes disponibilités peut être mis en place par divers moyens. Mais pour répondre aux exi-
gences de la DSI, la méthode la plus adéquate correspond à la conteneurisation des applications utilisées en
DevOps. Pour donner une définition simple de la conteneurisation : c’est le fait d’isoler chaque application
les unes des autres en les plaçant dans des boites appelées conteneur (”container” en anglais). Lorsqu’une
application est conteneurisée, ses dépendances sont sous contrôle. Avec une simple modification, on peut
changer de version, reconstruire, tester et déployer notre application, le tout sans interruption de service.
La conteneurisation est la solution idéale qui apporte à la fois de la robustesse et de la flexibilité nécessaire
pour répondre aux exigences définies par la DSI.
En outre, l’isolation des applications ne permet pas directement d’obtenir de la redondance sur le réseau.
Dans ce cas, on fait appel à un orchestrateur de conteneurs. Le but d’un orchestrateur est de déployer des
applications conteneurisées sur le réseau en assurant à la fois la redondance, l’augmentation et la réduction
des ressources en cas de fortes ou de faibles affluences.
Même si la majeur partie des applications peuvent être conteneurisé, certaines actions requièrent une
configuration manuelle des services. Ces configurations s’avèrent très chronophages lorsqu’un serveur
démarre, et peuvent être source d’erreurs, au même titre que les pannes et les maintenances système.
En ayant connaissance de ces informations, outre le fait de maı̂triser la conteneurisation et de savoir
mettre en place un cluster applicatif, il faut garder à l’esprit que chaque configuration faite manuellement
doit autant que possible être automatisée grâce à un script. Je perçois cette exigence, non pas comme des
compétences à acquérir pour mener à bien mon stage, mais plutôt comme une méthode de travail que je
pourrais réutiliser par la suite dans d’autres organismes.
Le DevOps est un concept qui a pour objectif d’unir les travaux des développeurs (dev) à ceux des admi-
nistrateurs système et d’infrastructures (ops).
A l’origine dans les grandes infrastructures, on trouve deux équipes isolées les unes des autres. D’un
coté il y a les développeurs, et de l’autre se trouve l’équipe opération qui est en charge de l’administration
système et du déploiement des logiciels. A cause de l’isolation entre ces deux équipes, le déploiement de
logiciel peut prendre plus de temps que nécessaire.
Le premier problème étant l’incompatibilité des dépendances des applications. En d’autres termes, l’équipe
des développeurs ne fournit pas une liste exhaustive des bibliothèques et autres fonctionnalités nécessaires
au bon fonctionnement de l’application. L’équipe des opérateurs se retrouve donc avec un logiciel qui ne
fonctionne pas, et donc impossible à déployer. Il se peut aussi que les développeurs et les opérateurs ne
possèdent pas les mêmes versions des dépendances de l’application, ce qui engendre des incompatibilités
entre les deux équipes.
Olivier Picard
L’utilisation du DevOps entraı̂ne parfois quelques modifications dans l’organisation d’un projet souvent
associé à l’idée de micro-services. Contrairement à la programmation traditionnelle appelée monolithique,
les micro-services découpent une application en différentes parties appelées services. Un programme mo-
nolithique est un programme complet découpé en objets ou en fonctions, ce qui forme un seul bloc de codes
interdépendants. Chaque fonction ou objet joue un rôle précis au sein de l’application et ne peut être séparé
les uns des autres. Par opposition, une architecture en micro-services est constituée de petites fonctions
appelées services ou modules qui s’exécutent en autonomie, et dont la vocation est d’effectuer parfaitement
une seule et unique tâche. L’architecture micro-services permet :
— d’obtenir une grande flexibilité du code
— la réutilisation des services au sein de différentes applications
— d’être facilement déployée sur des clusters hautes disponibilités et d’adapter la réplication des ser-
vices selon l’affluence
En revanche l’architecture en micro-services demande une réorganisation complète des structures habi-
tuelles. Chaque service est isolé les uns des autres et ne peuvent communiquer que par le réseau qui les
relie. La communication par le réseau étant plus lente que l’appel d’une fonction, par conséquent l’ap-
pel aux différents services doit se faire uniquement en cas de nécessité. Les services doivent être le plus
indépendants possible, afin d’éviter de solliciter un service externe.
Le DevOps présente un avantage majeur qui est la rapidité de déploiement des applications. Notamment
grâce au CI (Continuous Integration) /CD (Continuous Delivery). Le CI/CD est un principe fondamental du
DevOps. Il permet de fournir des mises à jour régulières et fiables aux clients. Un des avantages de mettre
en place le DevOps est qu’on peut faire facilement travailler plusieurs développeurs sur des fonctionna-
lités différentes d’un même logiciel. Ce travail en parallèle est déjà possible depuis de nombreuses années
par l’utilisation de dépôts telle que git, cnv ou autres. Cependant,la décomposition d’une infrastructure en
micro-services permet d’aller bien au-delà d’un dépôt git commun.
La difficulté qu’apporte le travail en parallèle, c’est l’intégration de toutes les fonctions codées séparément
au sein d’un même logiciel. Ce processus appelé le ”merge” est une tâche longue et fastidieuse qui requiert
un ou plusieurs jours. Dans certains organismes tels que la DSI de l’Université de la Réunion, on emploie
un intégrateur dont le rôle est de ”merger” toutes les modifications faites par les développeurs. L’avantage
que propose le CI est d’intégrer automatiquement toutes les modifications, pour former un logiciel complet
et ensuite le construire (build). L’écriture de tests d’intégration et de tests unitaires qui seront exécutés au-
tomatiquement par la machine est un moyen efficace de vérifier si le logiciel à été correctement assemblé,
et que chaque fonction réalise correctement leurs missions. Ainsi le rôle de la CI est d’intégrer, tester et de
construire les fonctions afin de créer un logiciel complet.
Une fois l’intégration terminée, on peut passer à la partie ”CD (Continuous Deployment)”. Le ”déploiement
continue”, comme son nom l’indique permet de déployer une application mais de manière automatique.
Avant de réaliser un déploiement, il faut s’assurer que la partie intégration est terminée et ne contient pas
d’erreur. Pour effectuer un déploiement, il faut que les développeurs écrivent au préalable des procédures
spécifiques qui permettent au code déployé d’être mis directement en production. Ainsi la machine suit les
instructions et diffuse l’application dans les référentiels adéquats. Du point de vue de l’utilisateur, l’appli-
cation proposée est toujours à jour.
Olivier Picard
Maintenant que j’ai parlé des principes fondamentaux du DevOps, je souhaite notifier qu’avant le stage,
je n’avais que très peu de notions relatives à ce sujet. Par conséquent, il fallait que je découvre et comprenne
les bases. Il me semble donc important que le chapitre suivant soit consacré aux compétences que je dois
acquérir, ainsi qu’à la méthode d’apprentissage que j’utilise.
7 MOOC et apprentissage
Le sujet du stage demande de posséder des connaissances très pointues dans de nombreux domaines,
notamment en système Linux. Mais la compétence la plus importante à acquérir est celle de la conteneu-
risation. Pour des raisons que j’ai déjà évoquées, c’est un élément très important qui permet de mettre en
place une fondation solide pour résoudre de nombreux problèmes, comme le déploiement automatique.
Comprendre et maı̂triser la conteneurisation d’applications est essentielle pour me permettre de mener à
bien mon stage. Pour aller un peu plus loin, cette philosophie et plus globalement le DevOps, sont des tech-
niques que je souhaite personnellement acquérir. Ce qui a été la principale raison pour laquelle j’ai choisi
ce stage. Ainsi l’autoformation a été une phase que j’ai beaucoup appréciée au cours de mon stage.
La technologie Docker constitue un pilier pour la conteneurisation. Ainsi la maı̂trise de cette technologie
est très importante. J’ai donc regardé de nombreuses vidéos YouTube, afin d’observer comment Docker est
utilisé par d’autres utilisateurs. Celles-ci m’ont permis de voir différents projets, différentes méthodes, et
différentes techniques, qui sont propres à chaque Youtuber. L’aspect pratique est très présent, ce qui me per-
met de comprendre très rapidement les fonctionnalités importantes, ainsi que les différents cas d’utilisation.
Ensuite je me fixe un objectif. En l’occurrence, un projet à réaliser. Dès le départ, afin de m’entraı̂ner,
mon tuteur m’a confié la réalisation d’un projet fictif. Ce projet est un ”raccourcisseur d’URL” (URL shor-
tener). Ce projet m’a aidé à guider mon apprentissage et constitue un objectif solide.
Dès lors que j’ai un objectif, les forums ainsi que la documentation officielle fournissent des points impor-
tants dans mon cheminement. A cette étape, je suis en mesure de comprendre les commandes principales, et
d’assembler les informations récupérées à partir de diverses sources. Le code repris sur internet est ensuite
légèrement modifié pour s’adapter à mes besoins. Ainsi les modifications et les recherches que j’effectue
me permettent de comprendre de mieux en mieux le fonctionnement de Docker, et de combiner toutes les
techniques des autres, afin d’en garder que les meilleures. Cette méthode d’apprentissage m’a grandement
aidé dans la progression de mes tâches durant mon stage.
Depuis le début du rapport je parle de conteneurs, de DevOps, et des problèmes qu’ils permettent de
résoudre. Mais je n’ai toutefois pas décrit le fonctionnement de ces technologies
7.2.1 Docker
Je ne peux pas parler de conteneurs sans parler de Docker. Docker est un outil qui permet de conteneuriser
une application. Comme je l’ai mentionné plus haut, la conteneurisation est le fait d’isoler une application
de son environnement. Avec Docker il y a deux mots qui sont omniprésents : les conteneurs et les images.
— Une image est une version immuable d’une application. Une image Docker fournit les dépendances,
les fichiers de configuration et tout ce qui est nécessaire à l’exécution de l’application. On peut
construire une image en utilisant un Dockerfile. Si on fait le parallèle avec la programmation orientée
objet, une image peut être comparée à une classe.
— Un conteneur (de l’anglais ’container’) est une instance d’une image. Ainsi, on peut créer autant
d’instances(conteneurs) que l’on souhaite basées sur une même image. En programmation orientée
objet une image peut être comparée à un objet.
Il faut aussi mentionner que par défaut une application conteneurisée est une application sans état dit
”stateless”. En quelques mots une application ’stateless’ est une application qui ne stocke pas des données
de manière persistante. Ainsi à chaque démarrage du conteneur, l’application est initialisée à son état d’ori-
gine. Pour donner un exemple : il est impossible de faire une base de données sur un modèle d’applications
’stateless’, puisque le but d’une base de données est de sauvegarder les données, donc c’est une applica-
tion dite ’stateful’. Toutefois, même si les applications Docker sont par défaut ’stateless’, il est possible
de les rendre ’stateful’. Pour ceci on leur rajoute un volume. Un volume est un espace disque qu’on attri-
bue au conteneur afin qu’il puisse conserver son état. L’avantage des applications conteneurisées est qu’ils
contiennent la totalité de leurs dépendances avec une version correcte pour le fonctionnement de l’applica-
tion. Cela implique que lorsque l’on transfert une image Docker, l’environnement de travail est déjà présent
et aucune configuration supplémentaire n’est requise. Ensuite, comme les conteneurs sont isolés les uns des
autres, c’est très simple de changer la version d’une application sans affecter les autres applications.
Ce sont tous ces avantages qui ont permis aux applications conteneurisées d’avoir une rapide adoption
dans la communauté des développeurs. La conteneurisation donc par conséquent Docker possède de nom-
breux autres avantages. Mais dans le cadre de mon stage cette technologie est au centre de toutes réflexions
et représente un point central du projet.
Olivier Picard
Si l’on l’analyse le problème, notre application écrit en PHP s’appuie sur le serveur Apache pour recevoir
les requêtes des clients. Mais d’un autre côté, la page web développée est dépendante de MariaDB. Il faut
noter que par défaut les images d’Apache sur DockerHub n’interprètent pas du code PHP. Cette contrainte
complexifie davantage notre tâche. Heureusement que le dépôt DockerHub dispose d’une image PHP basée
sur Apache ayant Debian 10 Buster comme système d’exploitation. Maintenant que je dispose d’une image
sur laquelle basée l’application, il ne reste plus qu’a faire le lien avec la base de données MariaDB. Pour
cela, il existe plusieurs méthodes. Une de ces méthodes est beaucoup plus classique, et consiste à écrire
un simple fichier Dockerfiles qui décrit les instructions pour construire notre image. Comme on doit faire
fonctionner plusieurs services (MariaDB et Apache), la solution la plus adéquate et la plus rapide dans ce
contexte est d’utiliser Docker Compose. A ce titre, il faut rédiger un fichier dans le language YAML qui
décrit les dépendances entre les différents services. (Se référer à l’annexe A pour plus de détails techniques)
Plus en détails, de la même manière que SSH, Docker Machine permet de prendre le contrôle à distance
des machines sur lesquelles il est installé. Cet outil est étroitement lié aux commandes présentes dans Do-
cker. A savoir, l’affichage des conteneurs en cours d’exécutions, la liste des images présente sur un noeud,
l’état ou l’adresse IP des machines. De plus, Docker Machine offre de nombreuses fonctionnalités liées
à la gestion d’hôtes distants tels que l’arrêt et le démarrage à distance d’une machine, mais aussi l’envoi
facilité d’un contenu. Comme mentionné précédemment, Docker Machine facilite grandement la création
de machine virtuelle ”dockerisée”. Ainsi, le déploiement est rendu beaucoup plus simple.
Toutefois, même si Docker Machine simplifie l’utilisation de docker sur les hôtes distants, une connec-
Olivier Picard
tion ssh classique peut tout aussi bien permettre le déploiement de conteneurs. Une fois connecté via ssh à
l’hôte, on peut utiliser les commandes docker habituelles, comme on le fait sur une machine locale.
9.2.1 Planification
Avant de commencer la configuration, j’ai conçu plusieurs machines à l’aide de Docker Machine. Ainsi
l’environnement de travail créé contient déjà tous les outils nécessaires pour le bon fonctionnement de
docker. Comme je reprends l’application ”urlshortener” qui consiste à raccourcir les url, j’ai donc conservé
la totalité du script créer précédemment, tout en effectuant des modifications sur la façon de le déployer.
On peut choisir différentes méthodes pour le déploiement :
— Docker CLI (en ligne de commande et avec des Dockerfile)
— Docker Swarm[10] (pour le déploiement automatique sur un cluster)
— Docker Compose (un fichier de configuration YAML, qui correspond à la même méthode que j’ai
utilisé précédemment)
Le plus approprié pour le déploiement sur un ensemble de machines est l’utilisation du Docker Swarm.
Cependant, je ne l’utiliserais pas maintenant, puisque Docker Swarm constitue un déploiement automatique
sur les hôtes distants. Or la mission est de déployer manuellement les services. Ainsi la méthode manuelle
me permet d’avoir de l’expérience dès lors où le déploiement se complexifie, mais surtout ça me permet
d’en apprendre d’avantage sur la communication entre les services, même lorsqu’ils sont dispatchés sur
différentes machines.
Dans ce cas précis, l’utilisation de Docker CLI (la version en ligne de commande de Docker Engine)
parait être un choix judicieux, mais possède un désavantage majeur. Comme il s’agit d’une succession de
commandes qui s’enchaı̂nent, c’est très facile de perdre le fil de ses idées. Par exemple, je me suis retrouvé
de nombreuses fois à exécuter des commandes sur la mauvaise machine. Par conséquent, j’ai été obligé de
réécrire des commandes pour stopper les conteneurs en fonctionnement sur le mauvais hôte, puis basculer
sur la bonne machine, et ensuite de nouveau déployer le conteneur. Si on exécute ces commandes à chaque
fois, ça devient rapidement fastidieux et source d’erreurs. Cependant, il est tout de même possible de créer
un script bash, pour exécuter les commandes de manière automatiques, ce qui limite les erreurs. J’ai pu
constater que les instructions des commandes de docker CLI sont compactes, peu lisibles et difficilement
compréhensibles. C’est pour ces raisons que je n’ai pas utilisé Docker CLI pour cette tâche.
En revanche, Docker Compose est le choix que j’ai fait. Dans le contexte du déploiement manuel sur plu-
sieurs hôtes, Docker Compose n’est pas le meilleur choix, mais c’est celui que je préfère et qui permet d’être
très efficace. La raison derrière ce choix est que le fichier de configuration de Docker Compose est écrit en
YAML. Les instructions sont faciles à lire, simples à comprendre et à apprendre. En utilisant Docker Com-
pose, je peux déployer mes services en utilisant une seule commande ‘docker-compose up --build‘ .
Les erreurs sont ainsi moins fréquentes, les modifications ainsi que le déploiement plus rapides
10 KeepAlived
10.1 Fonctionnement théorique et recherches
Keepalived[11] en quelques mots est une application qui permet à un service d’être davantage dispo-
nible mais aussi plus résistant aux pannes. KeepAlived utilise les protocoles VRRP[12] et ARP[13] pour
déterminer les machines en panne et ainsi switcher sur les machines en fonctionnement.
ARP (Address Resolution Protocol) : le protocole ARP est en réalité un ensemble de petits paquets qui
sont envoyés à intervalle régulière sur l’ensemble du réseau. Le but de ARP est de retrouver la machine
Olivier Picard
F IGURE 6: Schéma du fonctionnement de KeepAlived montrant le rôle de l’IP Virtuelle (image provenant du site web
’codeproject.com’
VRRP (Virtual Router Redundancy Protocol) : sans entrer dans les détails trop techniques du fonc-
tionnement de ce protocole, on peut dire qu’il permet à une machine de prévenir les routeurs alentour du
déplacement de l’adresse IP sur une nouvelle machine.
Keepalived est fourni avec une documentation très peu explicite sous forme de ”man” unix. Tout juste
quelques exemples sont disponibles pour la configuration de keepalived. C’est très complexe de définir
les paramètres existants et les positions de l’ensemble des fichiers de configuration. Heureusement que de
nombreux tutoriels sont présents sur internet, mais rares sont ceux qui donnent une configuration à la fois
concise et détaillée de keepalived.
Face à ce problème, ma première idée a été d’utiliser une image docker disponible sur DockerHub[14].
L’avantage d’utiliser une image, c’est qu’elle est déjà pré-configurée, et les modifications se font en définissant
des variables d’environnement dans le Dockerfile. De cette manière, j’évite toutes les configurations et je
dispose d’un KeepAlived fonctionnel dans les plus brefs délais. Avec cette méthode je deviens très produc-
tif, et je prends de l’avance sur mes autres tâches. Toutefois, cette méthode présente un désavantage majeur.
Il s’agit d’une image Docker non officielle. Cela implique qu’il n’y a pas de garantie d’obtenir un support
par le développeur. Comme KeepAlived a pour vocation d’être mis dans un environnement de production
utilisé par des milliers de personnes, mon tuteur m’a fortement déconseillé de me baser sur des images
Docker non officielles.
Après de longues recherches sur une manière simple de configurer KeepAlived, j’ai trouvé quelques
articles mais rien de concluant. Alors j’ai eu l’idée de prendre l’image docker non officielle, et de la
déconstruire (faire du reverse engineering). Par conséquent, j’ai pu déterminer les configurations à utili-
ser, ainsi que l’emplacement des fichiers dans la hiérarchie et encore bien plus d’informations nécessaires
au développement. De même, j’ai pu appliquer ce que j’ai trouvé pour disposer d’un KeepAlived fonction-
nel.
Les recherches que j’ai effectuées sur KeepAlived peuvent se résumer à quelques points importants :
— state MASTER — SLAVE : ce paramètre permet de définir un hôte comme le maı̂tre. C’est lui qui
répond aux requêtes.
— Dans le cas où plusieurs routeurs sont définis en tant que MASTER (maı̂tre) , dès que la
machine la plus prioritaire est en panne, le routeur un peu moins prioritaire s’autoproclame maı̂tre
sur le réseau. En revanche, si la machine plus prioritaire est de nouveau fonctionnelle, elle ne
reprend pas son statut de MASTER, elle reste passive.
— Lorsqu’il n’y a qu’un maı̂tre sur le réseau et que les autres sont définis comme SLAVE (esclave),
alors dès que la machine la plus prioritaire est de nouveau opérationnelle, elle reprend son statut
de maı̂tre et les machines les moins prioritaires deviennent à nouveau esclaves. C’est une variation
subtile mais qu’il est nécessaire de comprendre.
— interface xxxx : l’interface correspond simplement à l’interface à laquelle l’IP virtuelle sera associée.
— virtual router id xxx : l’identifiant du routeur virtuel est choisi au hasard et permet d’identifier le
routeur sur le réseau. Cet identifiant va de 1 jusqu’à 255. C’est un identifiant qui est distribué entre
tous les routeurs et qui partagent la ou les mêmes IP virtuelles.
— priority : définie la priorité du routeur. Plus un routeur est prioritaire, plus il est susceptible de de-
venir le maı̂tre. Le routeur le plus prioritaire s’autoproclame maı̂tre quand le maı̂tre actuel ne répond
plus.
— virtual ipaddress {xxx.xxx.xxx.xxx} : cette ou ces adresses IP correspondent aux IPs virtuelles
partagées par les routeurs du même réseau et du même ID. La machine maı̂tre sera donc accessible
par le ou les IPs définies avec ce paramètre
Comme KeepAlived est conçu pour faire du failover (basculement sur une machine fonctionnelle lorsque
la principale est en panne), c’est un pas de plus vers l’objectif de mon stage. KeepAlived constituera par la
suite l’élément indispensable pour la construction des clusters hautes disponibilités.
Olivier Picard
On ne peut pas pour l’instant introduire KeepAlived dans notre cluster, car on ne dispose pas de redon-
dance. Chaque service ne dispose que d’une seule instance sur le réseau. Pour résumer, on possède une
seule base de données et un seul serveur Apache qui exécute notre application. Notre objectif premier est
d’ajouter de la redondance, et ensuite de créer une relation maı̂tre/esclave entre les services redondants. Par
souci de simplicité, on duplique seulement notre application et non pas la base de données.
Pour ajouter une machine virtuelle et exécuter une copie du service sur cette nouvelle machine, seulement
quelques lignes suffisent :
Il faut se rappeler qu’on dispose déjà de deux machines virtuelles gérées par Docker Machine. La ma-
chine qui gère la base de données s’appelle ‘database,‘ et celle qui exécute notre application s’appelle
‘website. Ainsi grâce aux lignes de commandes ci-dessus, on ajoute la machine ‘website2. On peut vérifier
que tout fonctionne correctement en accédant via un navigateur à notre application en utilisant l’adresse IP
de website‘et de l’adresse IP de ‘website2‘.
Maintenant qu’on dispose de deux machines qui exécutent l’application, on peut utiliser KeepAlived pour
ajouter la relation de master/slave entre ces deux dernières.
On se connecte en ssh aux machines website‘et website2. Ensuite, on utilise les dépôts officiels pour
installer KeepAlived. Une fois téléchargé et installé, on peut procéder à la configuration de ce dernier en
utilisant les paramètres que j’ai décrit dans les recherches que j’ai effectuées. A présent, je peux configurer
les machines de la même façon que ci-dessous :
— state MASTER : défini pour les deux machines. Quand un esclave devient maı̂tre, il garde son état
jusqu’à sa ”mort”
— interface eth0 : défini sur les deux machines. Donc KeepAlived s’exécutera sur l’interface eth0
— Pour la priorité des routeurs virtuels :
— priority 100 : pour ‘website‘la priorité est 100
— priority 150 : pour ‘website2‘ la priorité est 150
— virtual ipaddress {192.168.1.10} : cette adresse IP est partagée par ‘website‘et website2. On pourra
par conséquent accéder à notre application avec cette adresse IP.
Avec cette configuration, l’application est maintenant bien disponible en utilisant l’adresse IP virtuelle.
A présent, l’application dispose de ce que l’on qualifie d’adresse de service.
Pour simuler une panne, j’éteins une des machines au hasard en essayant d’accéder à l’application de
raccourci d’URL. Tout se déroule comme prévu, et notre service a bien basculé sur la machine la moins
prioritaire. De cette manière l’application reste disponible, même si l’une des machines est en panne. Si l’on
souhaite créer encore plus de disponibilités en ajoutant un esclave supplémentaire, il suffit juste de suivre la
même procédure que celle présentée.
Ces deux machines qui exécutent l’application ont un lien master/slave, et se partagent une adresse IP
virtuelle. En d’autres termes, l’IP virtuelle n’est pas disponible sur les deux machines en même temps, c’est
KeepAlived qui attribue l’IP automatiquement. Cette IP est toujours attribuée à la machine la plus prioritaire
en activité. La question est de savoir comment démarrer notre service sur une IP fixe ? Sachant que la
machine esclave ne dispose pas de l’IP virtuelle tant que la machine maı̂tre fonctionne. Plus simplement, il
faut attendre que la machine la plus prioritaire soit en panne pour que l’IP virtuelle (l’IP fixe) soit définie sur
la machine esclave. Par conséquent, lorsque l’on essaie de démarrer le service Docker sur le maı̂tre, tout ce
passe bien parce qu’il dispose de l’IP virtuelle. Mais en ce qui concerne la machine esclave, le déploiement
échoue. Docker refuse de bind sur une adresse qui n’existe pas. Ce qui fait qu’on ne dispose que d’une seule
machine opérationnelle, et tout l’intérêt d’utiliser KeepAlived est perdu.
Le problème peut à première vue être une mauvaise configuration de Docker, ou un paramétrage man-
quant pour ce dernier. Mais il s’avère que c’est surtout un problème système. Avec Linux (Debian) on
dispose d’un paramètre qui permet de modifier ce comportement et d’autoriser à une application d’écouter
sur une adresse IP qui n’existe pas.
Dans le fichier ‘/etc/sysctl.conf‘on ajoute la ligne suivante
net.ipv4.ip_nonlocal_bind = 1
Maintenant on peut relancer le service sur la machine esclave, et docker réussira à démarrer l’application
avec succès. La raison pour laquelle Linux refuse de bind sur une adresse qui n’existe pas est simple.
Si une adresse IP n’existe pas, l’application qui utilise cette adresse inexistante ne recevra aucun paquet.
Pour éviter d’avoir des applications dont on est sûr qu’elles ne recevront pas de trafic, Linux bloque ce
comportement par défaut.
Pour l’instant j’utilise des machines créées et automatiquement configurées par Docker Machine, ce qui
accélère ma vitesse de travail. Bien que facile d’utilisation, ces machines ont le désavantage de ne pas dis-
poser de Debian Buster. Par conséquent, l’environnement de tests est très éloigné de celui de production.
De plus, je travaille sur mon ordinateur personnel et j’utilise une machine virtuelle Linux pour concevoir
les services. Ainsi lors de la création d’environnement avec Docker Machine, ce dernier crée une nouvelle
machine virtuelle. Par déduction, on a une machine virtuelle à l’intérieur d’une autre machine virtuelle, ce
qui n’est pas idéal pour les performances.
Par la suite, j’ai été amené à créer plusieurs VM (Virtual Machines ou en français Machines Virtuelles)
séparées les unes des autres, un peu comme si je disposais de plusieurs serveurs. Toutefois avec cette
méthode, il m’a fallu faire face à un nouveau défi, celui de faire communiquer toutes les machines entre
elles. Dans la pratique, il faut installer manuellement Docker, Docker Compose, Docker Machine, Kee-
pAlived, et quelques autres logiciels. Il n’y a pas de réelles différences entre les machines créées par Do-
cker Machine et celles créées manuellement. Toujours dans l’optique de disposer d’un environnement de
développement le plus proche possible de celui de la production, la mise en place d’un DNS est requis. Ce
qui nous mène au chapitre suivant.
Olivier Picard
F IGURE 8: Schéma très simplifié illustrant l’utilité d’un DNS (image provenant de ’kinsta.com’)
En quoi le DNS est utile pour mon stage ? Pour me rapprocher le plus possible de l’environnement de
production, mais aussi parce qu’il est plus facile de mémoriser un nom de domaine plutôt qu’une adresse
IP. Si le nom est court, il est plus facile et rapide à taper, donc je peux enchaı̂ner les tests plus rapidement.
La création de DNS n’est pas nouveau pour moi, puisque dans le cadre de mon cursus scolaire, j’en avais
déjà conçu un. Ce fut pour moi l’occasion de refaire cette expérience, et aussi de valider mes connaissances.
Je dispose de quatre machines en plus de la VM sur lesquelles je conçois les applications. Voici une liste
des machines ainsi que leur futur nom de domaine associé à une adresse IP
— dmt1 – nom de domaine : dmt1.vm – IP : 172.16.146.133
— dmt2 – nom de domaine : dmt2.vm – IP : 172.16.146.135
— dmt3 – nom de domaine : dmt3.vm – IP : 172.16.146.136
— reg – nom de domaine : reg.vm – IP : 172.16.146.134
Les machines dmt1, dmt2, dmt3 sont des serveurs virtuels réservés pour les tests. Bien que la machine
reg peut aussi être utilisée pour les tests, cette machine est réservée à un usage plus spécifique telle que
l’accueil du Bind9 (pour le DNS) et du registry de Docker. En ce qui concerne le registry, je le décrirai dans
un autre chapitre
Ware correspond à l’adresse 172.16.146.2 et le nom de mon interface réseau est ‘ens33. Alors on ajoute les
lignes suivantes au fichier de configuration de la machine ‘dmt1‘
auto ens33
iface ens33 inet static
address 172.16.146.133
netmask 255.255.255.0
gateway 172.16.146.2
Le fichier de configuration reste le même sur les machines reg, dmt2, dmt3. Seule l’adresse IP va varier
et sera remplacée par l’IP appropriée. Se reporter à l’annexe technique C pour avoir des détails sur la confi-
guration du DNS. Une fois le DNS en place, je peux continuer sur l’avancée de mes tâches, en particulier
sur le déploiement automatique de services en utilisant Docker Swarm.
Position sur le marché : développé à l’origine par Google, ces dernières années Kubernetes[17] s’est
imposé comme leader dans le monde des orchestrateurs. Il est largement utilisé sur les services clouds et
proposé par les plus grands fournisseurs cloud du monde tels que Amazon, Google, Microsoft Azure, mais
aussi Digital Ocean et bien d’autres. Face à une si grande popularité, Docker Swarm ne peut qu’occuper
un rôle d’orchestrateur secondaire. En revanche malgré un retrait certain, Swarm propose des avantages qui
peuvent s’avérer utiles pour certains projets.
Comparaison : pour aller droit au but, tout ce que Swarm propose comme fonctionnalités, Kubernetes
le propose aussi. En revanche, l’inverse n’est pas vrai. La majeure différence entre Kubernestes et Swarm,
réside dans le fait que Kubernetes offre beaucoup de paramètres, ce qui donne aussi beaucoup plus de
possibilités. On peut citer quelques exemples :
— Répartition de charge : avec Kubernetes on peut faire de la répartition de charge manuellement si on
le souhaite, tandis qu’avec Swarm une répartition de charge automatique est imposée. En outre, la
répartition de charge avec Swarm est un peu plus rapide qu’avec Kubernetes.
— Tableau de bord : par défault Kubernetes propose un espace pour surveiller le cluster. Cet espace
appelé dashboard fait parti intégrante de Kubernetes, tandis qu’avec Swarm cela nécessite l’ajout
d’outils supplémentaires.
— Prise en main : la prise en main de Kubernetes est très compliquée en comparaison à celle de Swarm
et c’est l’un des avantages majeurs de ce dernier.
— Démarrage sur une IP statique : avec Swarm il est impossible pour le moment de démarrer un service
sur une IP statique. Tandis que Kubernetes offre par défaut la possibilité qu’un service sur un cluster
soit accessible sur une IP fixe.
Docker Swarm est très adapté aux projets simples qui ne demandent pas des fonctionnalités très avancées,
ce qui permet une prise en main simple et rapide. Alors que Kubernetes est plus complexe à prendre en main
et demande plus de rigueur, mais offre un panel plus étendu de fonctions.
Proposition : après avoir pris connaissance des avantages et des inconvénients des deux orchestrateurs,
on peut à présent se demander, pourquoi utiliser Docker Swarm ? Est-ce qu’il ne serait pas plus intéressant
d’utiliser son concurrent Kubernetes ? Après réflexion, j’ai proposé à mon tuteur d’utiliser Kubernetes pour
réaliser mes tâches, ce qui me semblait être de mon point de vue plus intéressant. Malgré la pertinence de
cette proposition, Kubernetes ne peut être mis en place dans l’immédiat, ce qui demanderait une charge de
travail supplémentaire et un remaniement des configurations déjà existantes. Pour l’instant cela ne constitue
ni un besoin, ni une priorité pour l’Université de la Réunion.
14 Docker Swarm
Comme je l’ai mentionné précédemment, Docker Swarm est un outil qui permet l’orchestration des
conteneurs au sein d’un cluster. De ce fait avec un orchestrateur, on peut déployer automatiquement des
conteneurs sur un ensemble de machines appelé cluster.
Docker Swarm représente un pas important dans l’accomplissement de mes tâches, étant donné que c’est
une pièce maı̂tresse dans la construction de services hautes disponibilités.
Docker Swarm présente de nombreux avantages par rapport au déploiement manuel. On peut citer la rapi-
dité de déploiement, la cohésion facile à maintenir sur l’ensemble du cluster et l’ajustement des ressources
selon les besoins. Cependant la mise en place de Docker Swarm nécessite quelques adaptations et quelques
connaissances supplémentaires.
14.1 Théorie
14.1.1 Organisation
Avant de commencer, on doit disposer d’un ensemble de machines (cluster) qui sont sur le même réseau.
Ces machines doivent être en capacité de communiquer entre elles. Avec Docker Swarm on distingue deux
types de machines :
— Les managers (maı̂tre)
— Les workers (esclave)
Olivier Picard
F IGURE 9: Schéma technique illustrant la relation entre les managers et les workers. (image provenant de ’docker.com’)
Afin de former un cluster, il faut au minimum un noeud manager, mais optionnellement plusieurs peuvent
être ajoutés au cluster. Même si plusieurs managers peuvent coexister sur le réseau, ces derniers éliront un
seul et unique leader. Le rôle du leader est de distribuer les tâches sur les clusters en particulier sur les
workers. Autrement dit, le noeud manager leader se charge de l’orchestration, alors que les autres noeuds
managers ont pour rôle de distribuer les tâches aux workers. Par défaut malgré leurs statuts de ’manager’,
ils exécutent aussi les tâches au même titre que les workers. Néanmoins il est possible d’empêcher ce com-
portement, et de les utiliser exclusivement en tant que manager.
14.1.3 Registry
Supposons que l’on déploie nos services sur un ensemble de noeuds. Nos services se basent sur des
images personnalisées que l’on construit à l’aide de Dockerfile et ne sont par conséquent pas disponibles
sur ‘Docker Hub‘. Le problème qui se pose, c’est que les noeuds du cluster ne savent pas où télécharger les
images que l’on construit nous-mêmes. Si cette image n’est pas disponible sur ‘Docker Hub‘ ou en local,
il n’y a aucun moyen de les récupérer. Cependant, il existe une solution à ce problème. L’utilisation d’un
registry. Un registry est un dépôt où l’on stocke tous les images. Par exemple : ‘Docker Hub‘ est un registry.
Mais l’avantage d’un registry c’est qu’il peut être créé partout. Par conséquent, le registry personnalisé doit
être disponible pour l’ensemble des noeuds du cluster afin qu’ils accèdent aux images .
F IGURE 10: Schéma illustrant un cluster orchestré par Swarm, avec un manager, deux workers et un registry hors du
swarm mais accessible pour l’ensemble des services du cluster. L’IP de chaque machine est aussi annotée
Mon objectif est de reprendre notre application ”urlshortener” (raccourci d’url) et d’utiliser Docker
Swarm pour déployer automatiquement sur le cluster la base de données, ainsi que notre application web
basée sur le serveur web Apache.
Pour concevoir l’application ”urlshortener”, je crée une image personnalisée avec un Dockerfile basé
sur l’image php :Apache-buster. Cette image personnalisée me permet de copier mon fichier PHP dans le
conteneur, mais aussi d’installer les packages Debian pour avoir le plugin mysqli de PHP. Comme cette
image est créée par mes soins, elle n’existe que sur ma machine et ne peut être téléchargée sur DockerHub.
Par conséquent, un registry est nécessaire.
Olivier Picard
Sachant qu’on a deux services (une base de données et une application web), je vais donc choisir d’utili-
ser deux machines. On dispose alors d’un noeud manager qui sera en charge d’orchestrer, mais aussi d’un
autre noeud qui sera en charge de l’autre service. On ne peut prédire par avance l’attribution des services.
C’est le swarm qui se chargera de les répartir. Toutefois, il est important de noter qu’il existe des paramètres
pour déployer un service sur un noeud précis. Je détaillerai cette technique plus tard dans un autre chapitre.
Le cluster sera initialisé sur la machine ’reg’, et par conséquent ce noeud sera le noeud manager. Pour
initialiser le cluster Docker Swarm, on utilise la commande suivante :
l’option ’init --advertise-addr ADDRESS_IP’ n’est pas obligatoire. Par contre si la machine dis-
pose de plusieurs adresses IP, Swarm ne pourra pas choisir entre les différentes IP. Outre le fait d’initialiser
le noeud en tant que manager, le résultat de la console fourni une autre commande permettant à d’autres
machines de rejoindre le cluster en tant que worker. Cette commande est à copier sur les autres machines
afin qu’elles puissent rejoindre la cluster Swarm.
Maintenant que je dispose de notre manager, je vais me charger de la création du worker. Sur la deuxième
machine, je colle tout simplement la commande fournie par le manager lors de l’initialisation.
Le cluster dispose à présent d’un worker, donc la prochaine étape est de déployer notre application url
shortener sur ce cluster. Le point positif est qu’on dispose déjà d’un fichier docker-compose.yml qui décrit
les services qui constituent l’application. (Voir les chapitres précédents pour le détail et la création de ce
fichier).
2. L’utilisation de docker stack qui pourra être déployé sur le cluster Swarm.
Bien qu’à première vue les registry semblent être très techniques, ils constituent un élément fondamental
dans la mise en place de services hautes disponibilités. Concevoir des services qui s’adaptent aux besoins
et résistent aux pannes, c’est le rôle principal de Docker Swarm. Mais avant de déployer sur le Swarm, il
faut comprendre ce qu’est un registry ? Quel est son fonctionnement ? Mais aussi pourquoi les registry sont
essentiels à Docker Swarm ? L’aspect technique joue un rôle important dans la conception, mais aussi dans
la compréhension de la mission dans son ensemble. Il est aisé de mettre en place un registry non sécurisé
et disponible uniquement en local. Mais la tâche se complexifie lorsque l’on tente de le rendre accessible
depuis l’extérieur.
Registry local : ce type de registry est accessible uniquement en local. Ce qui en d’autres termes si-
gnifient qu’aucune machine ne peut y accéder. L’intérêt de ce type de registry est assez limité, mais peut
malgré tout être utilisé durant le développement pour effectuer des tests. Pour déployer un registry local, on
peut utiliser la commande ci-dessous :
Registry accessible à distance : ce type de registry est un peu plus complexe à mettre en place, mais
beaucoup plus utile. Bien que j’ai étudié les deux types de registry, je me pencherai plus vers les registry
qui autorisent les connections distantes. Un registry contient une majeure partie des éléments du cluster, et
par conséquent les données qu’il contient est potentiellement sensibles. Pour cette raison, si l’on souhaite
accéder à un registry depuis une autre machine, il faut absolument utiliser le protocole TLS. En résumé, ce
protocole permet de chiffrer les données qui transitent sur le réseau. Afin que ce protocole puisse sécuriser
la connection, il faut lui fournir ce que l’on appelle des certificats. Pour ce travail, je vais générer des ”cer-
tificats auto-signés”. En d’autres termes, je crée moi-même le certificat au lieu de passer par une autorité
de certification. Les certificats auto-signés ne doivent pas être utilisés en production. Je le fais uniquement
dans le cadre de mes tests.
Pour des informations détaillées sur la configuration d’un registry distant avec certificat auto-signé se
reporter à l’annexe D : création d’un registry
Il faut savoir que l’Université de la Réunion possède déjà son propre registry. Quelques images essen-
tielles au bon fonctionnement de l’organisme y sont stockées. Ainsi durant la phase de production, je ne mets
pas en place cet élément. Par contre, je dois être capable de configurer un registry pour simuler l’environne-
ment de production, et être à même de comprendre le fonctionnement général pour pouvoir éventuellement
lire les codes déjà existants.
Maintenant que l’application est disponible sur le cluster et orchestrée par docker swarm, je peux introduire
le prochain chapitre sur les ”reverse proxy” qui abordera une méthode pour accéder à notre application.
15 Traefik
F IGURE 11: Illustration du reverse proxy Traefik. L’illustration montre la liaison entre internet et l’infrastructure que
l’on déploie
Traefik[18] est un reverse proxy conçu en France qui concurrence le célèbre NGINX[19].
15.1 Définition
Un reverse proxy est un intermédiaire qui accueille les requêtes des utilisateurs depuis internet, et les
redirige sur le service approprié. Il se situe du côté serveur et peut être utilisé pour divers usages tels que :
— la compression de données
— pour vérifier qu’un utilisateur est correctement authentifié
— pour faire de la répartition de charge
— pour diriger une requête vers le bon service au sein d’un cluster
F IGURE 12: Schéma représentant mon objectif pour la réalisation et la composition du cluster. Traefik agit comme
point d’entrée du cluster. Il permet de configurer l’accès aux services tels que URL Shortener et MariaDB avec des
URLs personnalisables.
d’utilisation.
15.6 Difficultés
J’ai dépeint tous les avantages de Traefik, aussi je souhaite mentionner les nombreuses difficultés que
j’ai rencontrées avec cette technologie. Bien qu’une documentation soit fournie, mais dans la plupart des
cas lorsque l’on sort des sentiers battus, cette documentation est loin d’être suffisante. Seules les informa-
tions les plus essentielles sont présentes. En revanche, si l’on utilise de pair Traefik et Kubernetes, il y a
plus d’informations, et on peut résoudre les problèmes plus facilement. Lors de mon stage, mon tuteur m’a
demandé d’utiliser la combinaison Traefik + Docker Swarm ce qui est bien moins populaire et donc limite
grandement les articles sur le sujet.
16 ProxySQL
F IGURE 13: Shéma provenant de site officiel de ProxySQL, illustrant une configuration de base de données Mysql
incluant ProxySQL. Cette illustration montre une configuration avec une base de données en écriture et trois bases de
données Mysql en lecture
16.1 Fonctionnalités
Comme son nom l’indique, ProxySQL[20] est un proxy pour les bases de données SQL. Mais concrètement
ProxySQL est utile pour :
— Le failover (la redirection du trafic vers un noeud sain en cas de panne d’une base de données)
— Le sharding (le découpage d’une grande base de données en plusieurs petites bases de données)
— Faire office de pare-feu pour les données
— Séparer les requêtes en lecture de ceux en écriture, et les attribuer aux noeuds du cluster appropriés.
J’ai aussi utilisé la séparation et la redirection des requêtes selon leur nature, ce qui m’a permis de les ”load
balancer” intelligemment. Je reviendrai plus tard en détail sur ce point dans le rapport.
majeures pour laquelle cette technologie m’a été utile pour mon travail. Toutefois ProxySQL n’est pas le
seul proxy pour les bases de données Mysql sur le marché. Son concurrent le plus connu est HaProxy.
Comme on l’a vu dans le chapitre sur les reverses proxy, HaProxy fait aussi office de reverse proxy. Ha-
Proxy dispose d’une grande communauté, par conséquent la résolution de bugs est facilitée. Par ailleurs,
la séparation des requêtes en lecture de ceux en écriture demande un peu plus d’efforts à mettre en place
avec HaProxy. Comme ProxySQL s’est imposé à moi de par les différentes contraintes, je n’ai pas étudié
davantage HaProxy. Lors de mes recherches sur la séparation des requêtes en lecture de ceux en écriture,
j’ai vu beaucoup plus de tutoriels avec HaProxy, qu’avec ProxySQL.
17 Replication Manager
Réplication Manager[21] est un outil qui permet de configurer automatiquement un ensemble de base de
données. Cet outil permet d’ajouter et de configurer un proxy tel que HaProxy ou ProxySQL. Les confi-
gurations nécessaires pour faire fonctionner Replication Manager restent minimales. Juste avec quelques
configurations, je peux créer un cluster de base de données avec la relation maı̂tre-esclave.
17.1 Mission
L’objectif étant de concevoir des clusters hautes disponibilités composés de trois bases de données Ma-
riaDB, ainsi qu’un proxy ProxySQL, le tout conteneurisées avec Docker prêt à être déployées avec Swarm.
Une des contraintes est de minimiser les configurations manuelles, afin de diminuer les sources d’erreurs.
Pour ce travail, j’ai été assisté de mon tuteur puisque cela demande de maı̂triser de nombreuses compétences
à la fois. Pour effectuer cette tâche, j’ai dû comprendre et acquérir quelques rouages de l’administration de
base de données. A cette occasion, j’ai pour la première fois configuré manuellement les bases de données
avec une relation maı̂tre-esclave. J’ai aussi donné les droits d’accès en écriture au maı̂tre et les droits en
lecture aux esclaves. Ces bases de données sont répliquées et communiquent entre elles afin de se partager
les données de la base. Répliquer les données sur plusieurs bases est une technique qui permet d’effectuer
du load balancing, mais il existe d’autres méthodes. Une des méthodes s’appelle le sharding, mais son uti-
lisation présente quelques risques.
Supposons que notre cluster dispose que de deux machines. Notre cluster est fortement sollicité. Par
conséquent, le load balancing permet grandement d’alléger le serveur en répartissant la charge de travail
sur les deux serveurs. Imaginons maintenant qu’un de nos serveurs tombe soudainement en panne, il ne
reste donc plus qu’une seule machine. Comme il ne reste qu’un seul serveur, le load balancing n’est plus
fonctionnel, et la totalité du trafic doit être pris en charge par l’unique noeud du cluster. De ce fait, de nom-
breux ralentissements peuvent se faire ressentir.
Maintenant, imaginons que l’on dispose de trois noeuds sur notre cluster. Si l’un des noeuds est en panne,
il reste deux machines saines sur le cluster. Si la charge de travail est élevée, le load balancing est en place
pour répartir les opérations entre les deux noeuds. Ce qui fait qu’avec trois machines et malgré la panne
d’un serveur, les services restent hautement disponibles. Même si la probabilité que deux machines tombent
en panne en même temps soit faible, il reste une machine disponible pour s’assurer que le service reste ac-
cessible. En revanche avec deux machines si les deux noeuds sont en panne, les services n’existent plus.
Supposons qu’on dispose d’un cluster avec deux masters (maı̂tres) et un seul slave (esclave). Avec ce
Olivier Picard
type de configuration, il n’y pas réellement de problèmes majeurs si les bases de données sont correctement
configurées. Toutefois, cette configuration présente malgré tout un risque qui s’appelle le ”split brain”.
Avant d’aller plus loin, il faut d’abord définir la raison pour laquelle on utilise la relation maı̂tre esclave.
Il faut savoir que les bases de données maı̂tre ont les pleins pouvoirs sur les données. Autrement dit, ils sont
en capacité à la fois d’écrire, mais aussi de lire les données de la base de données. Quant aux esclaves, ils
sont plus limités, ils ont seulement le droit de lecture des données. Du coup, ils ne peuvent effectuer aucune
modification. Ainsi les requêtes qui impliquent la modification des données prises sont en charge par le
maı̂tre et les requêtes qui n’impliquent aucune modification sont réceptionnées par les esclaves.
Cela dépend du service, mais en règle générale il y a toujours plus d’opérations en lecture qu’en écriture.
A mon avis, il semble intéressant de mettre plus de serveurs dédiés à la lecture qu’à l’écriture, car on peut
effectuer du load balancing sur les esclaves, et les bases de données ne sont pas submergées par le trafic.
Ces explications posent les fondations de notre réflexion sans pour autant répondre à la question : ”Pour-
quoi avoir un seul maı̂tre sur le cluster ?”. Si nous prolongeons notre mode de réflexion, on peut constater
qu’il est possible de faire du load balancing sur les bases de données maı̂tres. Cette méthode aura les mêmes
résultats que d’avoir deux esclaves. Ce que je n’ai pas mentionné jusqu’à présent, c’est que dans une rela-
tion maı̂tre-esclave, les données sont répliquées sur l’ensemble du cluster. Ainsi les esclaves et les maı̂tres
disposent des mêmes données. Maintenant que l’on dispose de toutes les fondations nécessaires, on peut
expliquer le phénomène ”split-brain”.
Dans le contexte où l’on a deux masters qui sont load balancer, chacun d’entre eux va écrire les données
sur leur propre base de données. Ensuite, ils vont les répliquer vers l’autre master. Supposons à présent qu’il
y a une erreur de communication entre eux. Cela aura pour conséquence que chacun écrira les données de
leur coté sans pouvoir informer l’autre maı̂tre des modifications effectuées. Ils auront donc des bases de
données différentes les unes des autres. Si maintenant la connexion entre eux est rétablie, ils vont alors
resynchroniser les données. Cependant comme les données sont différentes, il ne sera pas possible de fu-
sionner les modifications. Le fait d’avoir chaque base de données qui fonctionne séparément, plutôt qu’en
lien l’une avec l’autre est appelé ”split-brain”. Toutefois, il est important de noter qu’il existe des algo-
rithmes qui permettent de fusionner les données.
Pour éviter le ”split-brain” et garder une conception simple du cluster. La configuration avec un master et
deux slaves paraı̂t la plus appropriée, puisque les esclaves ne sont pas autorisés à écrire les données. Donc
si la connexion se perd, une simple réplication permet d’ajouter les données manquantes.
17.4 Pourquoi utiliser replication manager
Maintenant que l’on a vu les raisons qui ont conduit à concevoir une architecture à trois machines,
avec deux masters et un slave, il semble opportun de donner plus de détails de Replication Manager. Pour
l’instant, j’ai fait les configurations des bases de données manuellement afin de mieux assimiler l’aspect
technique. Le but étant d’utiliser Replication Manager de manière qu’il configure automatiquement un
cluster de base de données. C’est à dire qu’aucune, ou peu d’interventions manuelles soient requises pour
éviter les sources de bugs.
Je dispose de trois machines qui exécutent MariaDB et qui fonctionnent indépendamment les unes des
autres. L’intérêt est de configurer Replication Manager pour qu’il puisse automatiquement prendre connais-
sance de son environnement et configurer à son tour les bases de données avec la relation maı̂tre-esclaves.
17.5 Difficultés
Avec Replication Manager, les difficultés ont été très nombreuses. Je dirai que c’est l’outil qui m’a posé
le plus de problèmes. Heureusement que pour certaines tâches, j’ai pu compter sur l’aide de mon tuteur.
Pour expliquer simplement, Replication Manager est un outil sans documentation. Où du moins ce qui
fait office de documentation est très minimale, et liste simplement les fonctionnalités les plus importantes
en les décrivant de façon très succinctes. J’ai pu constater que les explications qui y sont données visent
des utilisateurs qui ont déjà des connaissances poussées dans l’administration de base de données. Pour
avoir une vision complète du problème, l’organisme qui a conçu Replication Manager ne fournit pas une
documentation complète pour la simple et bonne raison que le support est payant pour l’intégrer dans
un système existant. Malgré tous ces inconvénients, Replication Manager dispose de nombreux exemples
(fichiers de configuration) qui aident à la compréhension,
Ce squelette est constitué des éléments principals au fonctionnement de la base de données MariaDB.
Plusieurs choix sont disponibles afin de déployer plus ou moins efficacement la base de données. On pour-
rait par exemple effectuer un changement dans la topologie, comme avoir deux Masters et un esclave, au
lieu d’un master et deux esclaves. On peut aussi remplacer ProxySQL par HAProxy. Ce ne sont là que
quelques exemples des choix possibles que l’on peut effectuer sur le cluster.
Pour résumer très brièvement, j’ai pour but de guider ces choix. Pour ce faire, je dois mettre en place une
série de tests afin d’obtenir des résultats concrets pour prendre les bonnes décisions. Chaque élément doit
Olivier Picard
être au maximum automatisé. L’intérêt du programme est de pouvoir mesurer les effets d’une panne sur le
système. Le but du cluster étant de ne pas perdre des données lors d’un incident dans le système. En plus
des fonctionnalités citées plus haut, l’algorithme doit aussi tester les performances du cluster MariaDB en
affichant un rapport avec le nombre d’opérations par seconde.
19 Conclusion
Ce stage m’a donné l’opportunité de travailler sur un projet déjà en production et utilisé par de nombreux
utilisateurs. Grâce à cette expérience, j’ai acquis de nombreuses méthodes de travail qui me seront utiles
pour gagner en productivité, ainsi qu’à l’amélioration de la maintenance des applications. Ces connaissances
m’ont permis de réaliser que l’automatisation des déploiements est une étape importante à ne pas négliger, et
qui doit être intégrée aussi tôt que possible. Avant même de commencer le développement d’une application,
j’essaie dorénavant de réfléchir à la gestion des erreurs, afin de diagnostiquer au plus tôt les pannes et les
comportements anormaux du programme. Bien que cela est illusoire de penser que toutes anomalies soient
détectées, la gestion d’erreurs aide dans quelques cas à détecter précisément la provenance du problème.
Outre les méthodes acquises, ce stage m’a permis de découvrir le DevOps qui est une pratique de plus en
plus demandée en entreprise, grâce à sa philosophie de déploiement continu. Pour le cluster MariaDB haute
disponibilité à déployer, il ne me reste qu’une seule étape. Cette étape concerne la réalisation des tests de
montée en charge et de fiabilité qui détermineront si la base de données est autorisée à entrer en phase de
production.
Olivier Picard
20 Annexes techniques
20.1 Annexe A : mise en place de Docker et Docker Compose
Notre fichier ”docker-compose.yml” se présente de la façon ci-dessous :
version: "3.7"
services:
db:
image: mariadb:latest
volumes:
- database:/var/lib/mysql
urlshort:
image: php:apache-buster
port:
- 8080:80
volume:
- ./index.php:/usr/src/index.php
volumes:
database:
Le fichier ”docker-compose.yml” ci-dessus permet de créer en quelques lignes à la fois la base de données
et l’application ”url shortner”. On dispose de deux services,
— Service ”db”
— ”image : mariadb :latest” : récupère l’image la plus récente de mariaDB sur DockerHub grâce à
la commande.
— ”volumes” : de part l’utilisation des volumes, on peut conserver de manière persistante nos
bases de données, ainsi que les tables et toutes les données qu’elles contiennent. En l’occur-
rence, on conservera dans le volume ”database” les fichiers du conteneur situés dans le répertoire
”/var/lib/mysql”
— Service ”urlshort”
— ”image : php :apache-buster” : ensuite, on définit le service ”urlshort” qui correspond à l’appli-
cation que l’on conçoit. Comme mentionné précédemment, on se base sur une image PHP qui
utilise un serveur Apache basé sur Debian Buster. Tout comme pour le service ”db”, l’image sera
récupérée sur le DockerHub.
— ”port : - 8080 :80” : par défaut le serveur Apache écoute sur l’ensemble des adresses, c’est à
dire sur 0.0.0.0 et sur le port 80. En sachant que le serveur Apache se trouve dans un conteneur,
il écoute donc sur l’adresse 0.0.0.0 et le port 80 à l’intérieur du conteneur. Le but ici est de
rendre accessible le port 80 du conteneur vers l’extérieur. C’est dans cette optique que l’on utilise
l’instruction ”port : - 8080 :80”. En d’autres termes, le port 80 du conteneur sera accessible depuis
l’extérieur sur le port 8080.
— ”volumes : ./index.php :/usr/src/index.php” : la particularité de ce service se situe au niveau du
volume. Dans ce contexte, le volume permet de copier notre fichier ”index.php” à l’intérieur
de notre conteneur. Dans notre conteneur, on peut donc retrouver le fichier index.php dans le
répertoire /usr/src/ .
— ”Le volume database” : à la fin du fichier, on retrouve le nom du volume utilisé par le service urlshort.
On spécifie le nom du volume ”database” dans la section volumes à la fin du fichier, de manière à le
conserver même lorsque le conteneur est arrêté. Si cette étape n’est pas effectuée, alors les données
de notre volume ne sont pas conservées.
Olivier Picard
Et enfin, j’exécute les deux fichiers docker-compose sur les machines appropriées pour démarrer les
serveurs.
eval "$(docker-machine env database)"
docker-compose --file docker-compose-db.yml up -d
Maintenant, notre site web est accessible via l’adresse IP donnée par la commande ci-dessous
docker-machine ip guestbook
20.2 Annexe C : configuration d’un DNS avec bind9
Pour concevoir le DNS, il faut ajouter des fichiers de configuration, notamment un fichier qui décrit les
adresses IP qui correspondent au nom DNS, mais aussi un autre fichier qui décrit les noms de domaine
gérés par le DNS. Le DNS ne représente pas une étape primordiale dans l’évolution de mon stage. Par
conséquent, seuls les points les plus importants de la création seront mentionnés.
Je crée un fichier ‘db.docker.univ-reunion.fr.zone‘ qui comporte les entrées suivantes
NS docker.univ-reunion.fr.
@ IN A 172.16.146.134
Par la suite, je crée le fichier ‘db.vm.zone‘qui gère le nom de domaine ‘vm‘. Ce nom de domaine n’a pas
pour vocation d’être en production, mais juste pour m’éviter de taper les adresses IP :
@ IN NS reg.vm.
reg IN A 172.16.146.134
dmt1 IN A 172.16.146.133
dmt2 IN A 172.16.146.135
dmt3 IN A 172.16.146.136
Maintenant que les fichiers zones sont créés, il reste à définir le fichier ‘named.conf.local‘.
zone "vm" {
type master;
file "/etc/bind/db.vm.zone";
};
zone "docker.univ-reunion.fr" {
type master;
file "/etc/bind/db.docker.univ-reunion.fr.zone";
};
cd ~
mkdir ~/certs/
openssl req \
-newkey rsa:4096 -nodes -sha256 -keyout certs/domain.key \
-x509 -days 365 -out certs/domain.crt
La deuxième étape est de créer notre registry. En suivant la documentation pour mettre nos certificats à
l’intérieur du conteneur, on utilise des volumes. On utilise le port 443 qui correspond au port utilisé par
TLS par défaut.
docker run -d \
--restart=always \
--name registry \
-v "$(pwd)"/certs:/certs \
-e REGISTRY_HTTP_ADDR=0.0.0.0:443 \
-e REGISTRY_HTTP_TLS_CERTIFICATE=/certs/domain.crt \
-e REGISTRY_HTTP_TLS_KEY=/certs/domain.key \
-p 443:443 \
registry:2
Le registry est créé, mais comme j’ai utilisé un certificat auto-signé, par défaut aucune machine ne peut
accéder au registry par manque de sécurité. Donc, sur toutes les machines qui utiliseront ce registry, il faut
ajouter la ligne ci-dessous afin de forcer docker à utiliser ce dernier. ’/etc/docker/daemon.json’
{
"insecure-registries" : ["NOM_DU_DOMAINE.EXTENSION"]
}
21 Annexe : gestion de projet
Tout au long de mon stage, l’organisation de mes tâches a été une priorité afin d’être le plus productif
possible, et d’organiser mon temps en conséquence. J’utilise Trello[22] qui est pour moi l’outil qui me
convient le mieux. Les raisons qui justifient ce choix sont :
— La conservation de toutes mes tâches dans une seule fenêtre
— Un visuel attractif
— La possibilité de définir les tâches en cours et celles réalisées, sans oublier celles à effectuer (TODO)
— La possibilité de grouper mes missions par leur thématique
— La possibilité de définir une date limite pour terminer une tâche
Trello n’est pas le seul outil qui permet d’organiser un projet. On peut citer ”GanttProject”[23] qui est un
outil basé sur la méthode Gant et qui permet de paralléliser au maximum les tâches.
Bien que j’ai organisé chacune de mes tâches et défini une date limite pour leur rendu, il est très com-
pliqué de planifier ce que l’on doit faire. Au début de mon stage, j’ai étudié Docker. Docker est un outil
très bien documenté avec une grande communauté qui l’entoure. Dans ce contexte, j’ai réussi à respecter le
délai que je me suis fixé. En revanche, dans la suite de mon stage, les documentations qui accompagnent
les outils que j’utilise se raréfient de plus en plus. Dès lors, le temps que je vais prendre pour comprendre
le fonctionnement de ces logiciels est beaucoup plus long que ce que j’avais initialement prévu.
Après une utilisation quotidienne des méthodes de gestion de projet, je suis mitigé sur la nécessité et
l’utilité de tels outils pour ma propre organisation. Les outils comme ”Trello”, ”GanttProject” sont avant
Olivier Picard
tout conçus pour regrouper et organiser une équipe autour d’un projet. Pour une utilisation individuelle, le
seul avantage que j’y vois est d’utiliser Trello comme ”TODO List”. Lorsque l’on découvre une technolo-
gie, et qu’on est en phase d’apprentissage sans avoir la maı̂trise de ce que l’on fait, il y aura de nombreux
imprévus. Ainsi dans ce contexte, il me semble futile d’essayer de me fixer à moi-même une contrainte de
temps pour finaliser mes tâches. En revanche, lorsque le nombre de tâches à réaliser est importantes les
TODO listes peuvent s’avérer utiles pour ne rien oublier.
Table des figures
1 Organigramme de la DSI . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 6
2 Architecture micro-services . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 10
3 Continuous Integration et Continuous Delivery (from AWS Website) . . . . . . . . . . . . 11
4 Récupération de MariaDB et PHP :Apache depuis Docker Hub, Construction d’une image
basée sur le Dockerfile qui contient l’application URL Shortener . . . . . . . . . . . . . . 15
5 Fonctionnement de Docker Machine (image provenant de Docker.com) . . . . . . . . . . 16
6 Schéma du fonctionnement de KeepAlived montrant le rôle de l’IP Virtuelle (image prove-
nant du site web ’codeproject.com’ . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 18
7 Fonctionnement de l’application URL Shortener en utilisant KeepAlived . . . . . . . . . . 20
8 Schéma très simplifié illustrant l’utilité d’un DNS (image provenant de ’kinsta.com’) . . . 24
9 Schéma technique illustrant la relation entre les managers et les workers. (image provenant
de ’docker.com’) . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 28
10 Schéma illustrant un cluster orchestré par Swarm, avec un manager, deux workers et un
registry hors du swarm mais accessible pour l’ensemble des services du cluster. L’IP de
chaque machine est aussi annotée . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 29
11 Illustration du reverse proxy Traefik. L’illustration montre la liaison entre internet et l’in-
frastructure que l’on déploie . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 32
12 Schéma représentant mon objectif pour la réalisation et la composition du cluster. Traefik
agit comme point d’entrée du cluster. Il permet de configurer l’accès aux services tels que
URL Shortener et MariaDB avec des URLs personnalisables. . . . . . . . . . . . . . . . 33
13 Shéma provenant de site officiel de ProxySQL, illustrant une configuration de base de
données Mysql incluant ProxySQL. Cette illustration montre une configuration avec une
base de données en écriture et trois bases de données Mysql en lecture . . . . . . . . . . . 35
14 Capture d’écran de mon organisation avec Trello . . . . . . . . . . . . . . . . . . . . . . 47
Olivier Picard
Références
[1] Dsi - https ://dsi.univ-reunion.fr.