Une bonne introduction au concept d'Observability qui englobe Logging, Monitoring, Tracing et Visualization.
1. Microservice First
Commencer par les microservices est non justifiable puisqu'ils ajoutent une complexité et des efforts supplémentaires aux développements.
Il faut plutôt débuter par des solutions monolithiques, ennuyeuses et classiques, pour évoluer selon le besoin vers des architectures microservices en identifiant les services qui nécessitent une refonte.
2. Gatekeeper et le versioning sémantique
Absence de stratégie de versioning : le partage des mêmes sources de données entre microservices peut ruiner la coordination, voire même ralentir les déploiements et freiner l'agilité.
"Gatekeeper" peut paraître à première vue la solution directe, n'est cependant qu’un déplacement du problème.
Le "Semantic Versioning" couplé à une bonne stratégie de gouvernance (héritage SOA) permettent la résolution de cette problématique.
3. Spiky load
Reste le partage des mêmes sources de données qui pose des soucis avec des charges non équilibrées entre services. L’exemple d’un microservice qui stresse une base de données commune et qui bloque les autres microservices.
L’utilisation des queues, pour amortir et absorber les pics et distribuer la charge, permet de résoudre le "Spiky load" entre services mais avec un coup supplémentaire de gestion du modèle asynchrone.
4. Discovery Service ou le centralised router
Le codage en dur des adresses et des ports IP simplifie le démarrage des projets. Mais très vite, il devient le cauchemar des Ops au moment du déploiement.
Tammer cite deux solutions :
La première est le "Discovery Service" comme consul ou etcd avec un effet de bord où les services seront obligés de comprendre les indirections de lookup.
Le "Centralised router" comme deuxième solution est considérée transparente et plus simple à mettre en place, étant la réplication d’un DNS.
5. Circuit Breaker pour les Dogpiles
Les "Dogpiles" : invoquer et continuer à stresser un microservice bien qu'il ne soit plus en état de répondre aux demandes, créant ainsi un effet boule de neige.
Une solution classique est l’introduction de "Circuit Breaker" qui jouera le rôle d'intermédiaire pour empêcher cet effet.
6. Correlation ID pour le débogage
Débogage : les microservices ajoutent des frais supplémentaires, y compris le débogage des services distribués et asynchrones. Ne pas concevoir une stratégie de logging dès le départ peut mettre en cause toute la solution.
L’utilisation de "Correlation ID" s'avère nécessaire pour tracer l’origine et le parcours des requêtes entre microservices. Évidemment, la gestion des id de corrélation ajoute un coût de développement et de coordination entre équipes.
7. Mocks
Lors de la phase de tests, les équipes ont tendance à créer des mocks pour les microservices utilisés. Ce qui finira par une prolifération des bouchons proportionnellement aux services consommés.
Une première solution serait de déléguer la création des mocks aux fournisseurs de services eux-mêmes, alors que les consommateurs doivent à leur tour savoir comment les invoquer. Pour répondre à cette limitation, il serait judicieux de développer une api qui, à la fois cache les détails d’implémentation et les protocoles de communication utilisés, mais aussi facilitant l’aiguillage entre les différentes implémentations pour les besoins de tests.
8. Flying Blind
"Flying Blind" ou l'expérience de s'aventurer en production sans avoir connaissance sur ce qui passe, ni sur les métriques d’utilisation de chaque microservice.
Les graphes, les alertes et les tableaux de bord sont les solutions classiques pour toute solution en production.
9. Snowflakes et Golden Image
"Snowflakes" : mettre à jour et installer les correctifs logiciels dans un univers microservices peut devenir ingérable, voire impossible.
"Golden Image" est une solution pour ce dilemme, avec l’utilisation d’une combinaison de base commune de frameworks et des runtimes avec des versions d’OS de références.
10. Doomsday et CI
Le "Doomsday", ou "La peur du jour J", le jour de la mise en production, est un problème récurrent pour les organisations qui ne déploient pas assez souvent. Déployer plus fréquemment augmente la confiance en son processus de déploiement, réduit les risques d'erreur, et améliore la rapidité à laquelle on peut délivrer de nouvelles fonctionnalités.
L'intégration continue résout cette problématique avec la mise en place d'une pipeline prédéfinie et qui donne confiance aux tests automatisés.
11. PaaS
L’explosion opérationnelle avec l’utilisation d’une grande variété de technologies, de langages et de solutions, ce qui rend leur gestion en post-production un fardeau poussant les Ops à bloquer le passage en production.
Automatiser le déploiement (CD) s'avère à première vue impossible. Mais c’est là où le rôle des platformes PaaS se confirme pour donner la souplesse et les moyens de gestion des microservices.
Recensement des design patterns existantes pour les architectures microservices
Une demo fournie par Red Hat pour deployer une architecture microservices basée sur Kubernetes, Openshift et Spring Cloud / Netflix OSS avec Ansible.
EDIT:
- Les repos Git Hub avec la conf Ansible et le code source des demos est ici: https://github.com/redhat-helloworld-msa
- Une video condensée de 11 min présente le projet: https://developers.redhat.com/blog/2016/07/27/have-your-own-microservices-playground/
Une comparaison des approches fournies par Spring Cloud / Netflix OSS et Kubernetes pour résoudre les problématiques des architectures microservices.
La gestion des datas dans une architecture microservices.
Ça parle de DDD, eventual consistency, CQRS, ...
C'est clairement orienté dev mais permet également d'introduire rapidement ses concepts à ceux qui y sont moins familiers.
Une autre comparaison de Kubernetes et SpringCloud pour une archi microservice
Une série d'article présentant les bases d'une archi microservices utilisant les outils de SpringCloud (Eureka, Zuul & Hystrix)
Une bonne introduction à Apache Mesos pour orchestrer des application sous forme de Cgroups ou de containers Docker
Comment construire des images d'applications unikernels OSv avec Docker
Un repository fournissant les Makefiles et la configuration pour créer des applications unikernels OSv à partir de pas mal d'applis (ex: haproxy, jetty, mysql, tomcat, ...)
L'article parle des optimisations apportés par les applications unikernels.
Nomad fourni des services de gestion de cluster et d'ordonnancement de jobs en environnement cloud. C'est fait par Hashicorp, la boite qui développe Vagrant, Terraform et plein d'autres outils sympa.
Dans un contexte d'architecture microservices utilisant des containers et le concept ImmutableServer, l'utilisation d'un serveur d'application java (tomcat...) fournit uniquement le framework (servlets, ...) nécessaire à l'application java.
Les fonctionnalités de gestion des applications (plusieurs applis dans la même JVM, déploiement à chaud, ...) sont en effet directement gérées au niveau containers (1 applis = 1 JVM = 1 container, déploiement d'un nouveau container en cas de mise à jour de l'applis).
En fin d'article, il est également question de SpringBoot (http://projects.spring.io/spring-boot/) et CamelBoot (https://camel.apache.org/camel-boot) qui permettent de démarrer directement une JVM avec son framework sans toute la lourdeur du serveur d'application.
Une très bonne présentation de l'architecture microservices par Xebia:
1) un microservice = un fonction qui possède:
- son propre code
- ses propres datas
- un ou plusieurs processus distinct
2) Chaque service doit-être complètement indépendant des autres en termes de :
- modification => changement de code sans impacts sur les autres services
- scalabilité => modification du nombre d'instance sans impacts sur les autres services
3) Toute la communication avec l’extérieur doit se faire via la couche réseau (REST ou BUS).
La suite de l'article ici:
http://blog.xebia.fr/2015/03/09/microservices-des-architectures/
http://blog.xebia.fr/2015/03/16/microservices-des-pieges/
Méthodologie pour construire des applications faites pour une utilisation de type cloud:
- 1 application = 1 repository de code et 1 seul
- toutes les dépendances doivent-être explicites et fournies avec l'application
- la configuration doit-être gérée dans des variables d'environnements
- tous les services externes (api, database, smtp, cache, messaging...) doivent-être gérés comme des ressources accessibles via une URL
- les étapes de build (compilation + dépendances), release (application configuration) et run (lancement de l'application) doivent être strictement séparées
- l'application doit-être stateless et "share-nothing" (aucune donnée en local)
- l'application doit gérer sa couche réseau sans dépendre d'un logiciel externe (ex: webserver embarqué pour ne pas dépendre d'apache)
- l'application doit-être composés de process instanciables sur le même serveur ou sur différents serveurs (scalabilité)
- les process ne doivent pas être démarrés en taches de font (démon) par l'application. la gestion des process (arrêt/relance, gestion logs et stdout, ...) doit être délégués à un process manager (systemd, runit, foreman, ...)
- les tâches administratives (ex: migration db, ...) doivent être traitées par des process séparées (scripts) mais fournis avec le code applicatif et lancé dans le même environnement applicatif
Explication des contraintes et des solutions pour utiliser une application Legacy qui écrit ses données sur disque dans un contexte de cloud où chaque serveur doit avoir les mêmes données