Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Checklist pour concevoir une application dans le cloud: 10 conseils à l’attention des concepteurs et architectes

Checklist pour concevoir une application dans le cloud: 10 conseils à l’attention des concepteurs et architectes

Kubernetes est aujourd'hui le standard pour déployer des applications de toutes sortes: api, batchs, microservices et même des monolithes!
Il apporte des solutions à beaucoup de problèmes mais aussi une grande complexité.
Il peut donc être très difficile pour les développeurs et concepteurs d'identifier les contraintes d'une telle architecture.

Dans cette présentation, vous (re)découvrirez dix astuces et conseils que j'ai pu appliquer et qui m'ont aidé dans mes derniers projets.

Ces derniers traiteront :
* du choix des solutions techologiques
* du développement
* des contraintes de conception liées à K8S
* et plus encore !

33003e72c00afccb1b1989e1ec21d21d?s=128

Alexandre Touret

February 04, 2022
Tweet

More Decks by Alexandre Touret

Other Decks in Technology

Transcript

  1. Checklist pour concevoir une application dans le cloud: 10 conseils

    à l’attention des concepteurs et architectes 1
  2. 2022 Merci à nos sponsors

  3. Alexandre Touret Architecte / Développeur #Java #API #CI #Cloud #Software_Craftsmanship

    3 @touret_alex https://blog.touret.info
  4. Un peu de contexte ... 1.

  5. 5

  6. Technologies utilisées 6

  7. En avez vous VRAIMENT besoin ?

  8. Application gestion Périmètre maîtrisé Déploiement déjà automatisé 8

  9. Quelles sont les contraintes techniques? Avez-vous des SLOs contraignantes? (ex.

    disponibilité supérieure à 99%) Avez vous vraiment besoin de scaler dynamiquement votre application ? 9
  10. Mise à disposition d’environnements 10 Avez vous besoin de délivrer

    des environnements à la demande (et très rapidement)?
  11. Les bases de Docker & Cie

  12. 12

  13. Il vous faudra connaître 13

  14. 14

  15. De mon côté…

  16. Le contexte

  17. « les organisations qui conçoivent des systèmes [...] tendent inévitablement

    à produire des designs qui sont des copies de la structure de communication de leur organisation. » — M. Conway 17
  18. Quel est le RACI ? Est-ce que votre organisation est

    compatible ? 18 RACI & Responsabilités
  19. Les applications stateless et les autres ...

  20. 20 Codebase One codebase tracked in revision control, many deploys

    Dependencies Explicitly declare and isolate dependencies Config Store config in the environment Backing Services Treat backing services as attached resources Build, release, run Strictly separate build and run stages Backing Services Treat backing services as attached resources Processes Execute the app as one or more stateless processes Port Binding Export services via port binding Disposability Maximize robustness with fast startup and graceful shutdown Dev/prod parity Keep development, staging, and production as similar as possible Logs Treat logs as event streams Admin processes Run admin/management tasks as one-off processes Source: https://12factors.net
  21. 21 Pour une API Port Binding Disposability Dev Prod Parity

    Processes Config Concurrency
  22. Démarrage (rapide) de l’application

  23. 23

  24. Comment faire avec Spring Boot? • Vérifiez d’abord vos NFRs

    • Activez le lazy loading spring.main.lazy-initialization=true • Désactivez l’autoconfiguration et utilisez l’annotation @Import • Activez le graceful shutdown server.shutdown=graceful
  25. Bien choisir ses frameworks et environnements d’exécution

  26. 26

  27. 27 Items à identifier ✓ Rapidité du démarrage ✓ Gestion

    des arrêts ✓ Capacité à s’intégrer dans Docker et K8S ✓ Observabilité ✓ Mémoire et CPU utilisées ✓ Gestion des dépendances et du patch management
  28. L’ observabilité

  29. Adresser sur ce sujet dès la conception ! Ne pas

    attendre la mise en production :) Exposer via des endpoints REST l’état de votre système Faire attention aux FRAMEWORKS utilisés 29
  30. liveness & readiness probes livenessProbe: failureThreshold: 3 httpGet: path: /actuator/health/liveness

    port: http scheme: HTTP initialDelaySeconds: 30 periodSeconds: 10 successThreshold: 1 timeoutSeconds: 1 30 readinessProbe: failureThreshold: 3 httpGet: path: /actuator/health/readiness port: http scheme: HTTP initialDelaySeconds: 30 periodSeconds: 30 successThreshold: 1 timeoutSeconds: 1
  31. Spring Actuator dependencies { implementation 'org.springframework.boot:spring-boot- starter-actuator' } https://docs.spring.io/spring-boot/docs/current/reference/html/actuator.html

  32. Spring Actuator management.health.probes.enabled=true management.endpoints.enabled-by-default=true management.health.livenessstate.enabled=true management.health.readinessstate.enabled=true management.endpoint.health.show-details=always management.endpoint.health.probes.enabled=true management.endpoint.health.enabled=true LivenessStateHealthIndicator

    & ReadinessStateHealthIndicator 32
  33. 33 @Component public class MongoDBActuatorHealthIndicator implements HealthIndicator { [...] @Override

    public Health health() { // ping database } @Override public Health getHealth(boolean includeDetails) { if (!includeDetails) { return health(); } else { var statuses = mongoDBHealthService.findStatusForAllConfigurations(); return Health.status(checkStatus(statuses)).withDetails(statuses).build(); } } [...] }
  34. Monitoring ▪ Micrometer ▪ Prometheus ▪ Grafana 34

  35. Micrometer • Permet d’exporter des métriques (par ex. Le TTR

    d’une API en utilisant l’annotation @Timed) • Ces métriques peuvent être agrégées dans Prometheus dependencies { implementation 'io.micrometer:micrometer-registry-prometheus’ }
  36. 36 management: endpoints: enabled-by-default: true web: exposure: include: '*' jmx:

    exposure: include: '*' endpoint: health: show-details: always enabled: true probes: enabled: true shutdown: enabled: true prometheus: enabled: true metrics: enabled: true health: livenessstate: enabled: true readinessstate: enabled: true datasource: enabled: true metrics: web: client: request: autotime: enabled: true Actuator configuration Metrics configuration
  37. La CI/CD

  38. Deux sortes de pipelines • Création plateforme • Build &

    Deploy
  39. Platform provisionning terraform apply

  40. Application build & deploy Build •Application Java •Image Docker •Chart

    Helm Tests •Tests unitaires et d’integration •Smoke tests de la nouvelle image Docker Deployment •Déploiement continu de la branche develop •Déploiement de la release
  41. Exemple Migration Spring Boot, Image Docker, JDK Testé en local

    → Dev → Recette ⇒ En 1 jour 41
  42. La configuration

  43. Comment configurer votre application cloud native? 43 ▪ Variables d’environnement

    ▪ Config Maps ▪ Secrets
  44. Les variables d’environnement spec: containers: - env: - name: JAVA_OPTS

    value: >- -XX:+UseContainerSupport -XX:MaxRAMPercentage=70.0 -Dfile.encoding=UTF-8 - Djava.security.egd=file:/dev/./urandom 44
  45. Les config maps apiVersion: v1 kind: ConfigMap metadata: creationTimestamp: 2021-03-11T18:38:34Z

    name: my-config-map [...] data: JAVA_OPTS: >- -XX:+UseContainerSupport -XX:MaxRAMPercentage=70.0 -Dfile.encoding=UTF-8 -Djava.security.egd=file:/dev/./urandom 45
  46. Quid des fichiers de configuration ? On peut les spécifier

    “comme des variables” directement dans les config maps On peut les externaliser 46
  47. Les fichiers dans les config maps volumeMounts: - mountPath: /config

    name: configuration-volume readOnly: true [...] volumes: - configMap: defaultMode: 420 name: configuration name: configuration-volume 47 apiVersion: v1 kind: ConfigMap [...] data: my.conf: {{- (.Files.Glob "conf/*").AsConfig | nindent 2 }}
  48. Limitations ▪ Error: UPGRADE FAILED: ConfigMap "my- service" is invalid:

    data: Too long: must have at most 1048576 characters
  49. Externaliser les valeurs apiVersion: autoscaling/v1 kind: HorizontalPodAutoscaler metadata: labels: [...]

    spec: maxReplicas: {{ .Values.myapp.maxReplicaCount }} minReplicas: {{ .Values.myapp.minReplicaCount }} [...] targetCPUUtilizationPercentage: {{ .Values.myapp.replicationThreesold }} 49
  50. Le fichier values.yml myapp: minReplicaCount: "2" maxReplicaCount: "6" replicationThreesold: 80

    50
  51. Les templates de fichier apiVersion: v1 kind: ConfigMap metadata: name:

    configuration labels: [...] data: application.properties: |- {{ tpl (.Files.Get "conf/application.properties") . | nindent 4}} 51
  52. Les templates Le fichier application.properties logging.level.org.hibernate.stat={{ .Values.configmap.application.org_hib ernate_stat }} logging.level.org.springframework.sec

    urity={{ .Values.configmap.application.org_spr ingframework_security }} 52 Le fichier values.yml configmap: application: org_hibernate_stat: ERROR org_springframework_security: ERROR
  53. Les fichiers binaires apiVersion: v1 # Definition of secrets kind:

    Secret [...] type: Opaque # Inclusion of binary configuration files data: my_keystore.jks: {{ .Files.Get "secrets/my_keystore.jks" | b64enc }} 53
  54. Logger efficacement

  55. L’utilisation des logs Dans la console: kubectl logs --tail Agrégateur

    de logs (ex. ELK) 55
  56. Flux de sortie des containers Docker stdout & stderr Inutile

    de configurer la sortie vers des fichiers 56
  57. Bonnes pratiques Indiquer dans vos LOGS: Les éléments de votre

    conteneur (Image, containerID,...) Les éléments de contexte K8S (IP POD, ID POD, namespace,...) Log4j Docker Support – Log4j Kubernetes Support 57
  58. Pour aller plus loin Vous pouvez logger et tracer les

    appels à vos APIS: Requête, ID de l’appelant, ID de corrélation,... zalando/logbook: An extensible Java library for HTTP request and response logging 58
  59. Distributed tracing Vous pouvez identifier et corréler vos différents appels

    dans votre plateforme microservices en implémentant OpenTracing. 59
  60. 60

  61. Sur GCP ▪ Vous avez par défaut: □ Un explorateur

    de logs (Google Logs Explorer ~ELK) □ Un rapport d’ erreurs (~ dashboard ELK) □ Un analyseur de traces distribuées 61
  62. Logging ▪ Utilisez Spring Cloud GCP Starter dependencies { implementation("com.google.cloud:spring-cloud-gcp-starter-logging")

    } ▪ Utilisez Logback comme framework de Logging ▪ Initialisez les variables GOOGLE_CLOUD_PROJECT & GOOGLE_APPLICATION_CREDENTIALS dans vos charts HELM 62
  63. 63

  64. Error Reporter ▪ Par défaut, il agrège toutes les erreurs

    de votre plateforme ▪ Vous pouvez également ajouter vos erreurs business (ex. HTTP 500) ▪ Vous pouvez intégrer votre application grâce à des appenders Logback 64
  65. 65

  66. Distributed tracing ▪ By using Spring Cloud GCP starter trace

    dependencies { compile group: 'org.springframework.cloud', name: 'spring-cloud-gcp-starter-trace’ } 66
  67. En résumé 67

  68. Evitez le hype driven development Pensez à votre organisation Travaillez

    sur l’observabilité dès les premières étapes Automatisez tout (ou presque)
  69. Merci! Des questions? 69

  70. https://roti.express/r/sc22-046