Skip to Content
BackendSpring Boot Actuator

Spring Boot Actuator

Monitoring, diagnostics et sondes de santé pour les applications Spring Boot en production.

Activer le starter

Ajouter dans le pom.xml :

<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-actuator</artifactId> </dependency>

Sans ce starter, aucun endpoint n’est exposé — même avec une configuration manuelle.

Endpoints disponibles

Par défaut, Spring Boot expose health et info sur /actuator. Tous les autres requièrent une activation explicite.

EndpointCe qu’il retourne
/actuator/healthÉtat de santé (UP, DOWN, OUT_OF_SERVICE)
/actuator/infoInformations libres (ex. version, description)
/actuator/metricsListe des métriques disponibles
/actuator/metrics/{nom}Valeur d’une métrique spécifique
/actuator/envPropriétés de configuration résolues
/actuator/beansTous les beans Spring, leur type et leur dépendance
/actuator/conditionsClasses @Conditional — pourquoi certains beans sont ou ne sont pas créés
/actuator/threaddumpSnapshot des threads JVM
/actuator/loggersNiveaux de log configurés et modifiables (Logging)
/actuator/httptraceHistorique des requêtes HTTP (nécessite spring-boot-starter-web classique, pas WebFlux)
/actuator/gateway/routesRoutes actives Spring Cloud Gateway (uniquement dans un projet Gateway)
/actuator/prometheusFormat Prometheus pour Grafana/Prometheus

Règle : n’activer que ce qui est utile. env et beans en production révèlent des secrets de configuration.

Configuration YAML de base

management: endpoints: web: exposure: include: health,info,metrics base-path: /actuator path-mapping: health: status endpoint: health: show-details: when-authorized show-components: always health: liveness: state: enabled: true readiness: state: enabled: true

Pourquoi path-mapping: health: status ?

Les sondes Kubernetes et Docker vérifient /status par convention. L’alias permet de garder le chemin standard Spring Boot (/actuator/health) pour le debug, tout en servant les sondes sur /actuator/status.

Voir aussi : pour les patterns de configuration application.yml (profils, dépendances entre propriétés, validation), consulter Spring Boot — application.yml.

Sécurité — Masquer les endpoints sensibles

Sans Spring Security, tous les endpoints sont accessibles sans authentification. Dès que Spring Security est dans le classpath, les endpoints * ne sont plus publics. Pour autoriser l’accès public à certains endpoints (ex. sondes Kubernetes) et garder le reste restreint, voir aussi Authentification API pour le pattern d’authentification global du service.

import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.security.config.annotation.web.builders.HttpSecurity; import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity; @Configuration @EnableWebSecurity public class ActuatorSecurity { @Bean public SecurityFilterChain securityFilterChain(HttpSecurity http) throws Exception { http .authorizeHttpRequests(auth -> auth .requestMatchers("/actuator/health", "/actuator/info", "/actuator/status").permitAll() .requestMatchers("/actuator/**").hasRole("ADMIN") ) .csrf(csrf -> csrf.disable()); return http.build(); } }

Piège : management.endpoints.web.exposure.include=* expose threaddump, env, beans, loggers à quiconque connaît l’URL. En production, limiter à health,info,prometheus.

Endpoints personnalisés

HealthIndicator

Ajouter une dépendance à la liste UP/DOWN d’un composant externe.

import org.springframework.boot.actuate.health.Health; import org.springframework.boot.actuate.health.HealthIndicator; import org.springframework.stereotype.Component; @Component public class BaseDeDonneesHealthIndicator implements HealthIndicator { private final BaseDeDonneesClient client; public BaseDeDonneesHealthIndicator(BaseDeDonneesClient client) { this.client = client; } @Override public Health health() { try { client.ping(); return Health.up() .withDetail("driver", client.getDriverName()) .withDetail("latencyMs", client.getLastPingMs()) .build(); } catch (Exception e) { return Health.down() .withException(e) .withDetail("reason", "Impossible de joindre la base") .build(); } } }

Le résultat dans /actuator/health :

{ "status": "UP", "components": { "db": { "status": "UP", "details": { "driver": "postgresql", "latencyMs": 3 } }, "diskSpace": { "status": "UP", "details": { "total": 53687091200, "free": 21474836480, "threshold": 10485760 } } } }

InfoContributor

Exposer des informations personnalisées dans /actuator/info :

import org.springframework.boot.actuate.info.Info; import org.springframework.boot.actuate.info.InfoContributor; import org.springframework.stereotype.Component; @Component public class InfoContributorBuild implements InfoContributor { @Override public void contribute(Info.Builder builder) { builder.withDetail("build", Map.of( "commit", System.getenv("GIT_COMMIT", "unknown"), "version", System.getenv("APP_VERSION", "dev"), "timestamp", System.currentTimeMillis() )); } }

Sondes Kubernetes

Pour un déploiement Kubernetes, activer les sondes liveness et readiness :

management: endpoint: health: probes: enabled: true health: liveness: state: enabled: true readiness: state: enabled: true

Cela expose automatiquement :

  • /actuator/health/liveness — sonde de survie (k8s = /health/live)
  • /actuator/health/readiness — sonde de prêt (k8s = /health/ready)

Attention : l’URL réelle est /actuator/health/liveness (le préfixe /actuator est ajouté automatiquement). Vérifier avec curl http://localhost:8080/actuator/health/liveness.

Déclarer les sondes dans le Deployment Kubernetes

apiVersion: apps/v1 kind: Deployment spec: template: spec: containers: - name: mon-service livenessProbe: httpGet: path: /actuator/health/liveness port: 8080 initialDelaySeconds: 30 periodSeconds: 10 readinessProbe: httpGet: path: /actuator/health/readiness port: 8080 initialDelaySeconds: 10 periodSeconds: 5

Attention : si un path-mapping: health: status est configuré (voir section « Configuration YAML de base »), les chemins des sondes sont aussi remappés. Adapter le Deployment Kubernetes :

livenessProbe: httpGet: path: /actuator/status/liveness port: 8080 readinessProbe: httpGet: path: /actuator/status/readiness port: 8080

Intégration Prometheus + Grafana

Activer l’endpoint prometheus et exporter les métriques :

management: endpoints: web: exposure: include: health,metrics,prometheus metrics: export: prometheus: enabled: true tags: application: ${spring.application.name}

Métriques JVM automatiques :

  • jvm_memory_used_bytes — mémoire utilisée par zone
  • jvm_threads_states — threads par état (running, blocked, …)
  • jvm_gc_pause_seconds — pauses du garbage collector
  • http_server_requests_seconds — latence des requêtes HTTP
  • process_cpu_usage — utilisation CPU du processus

Pièges courants

1. Exposition inadvertée d’env en production

# ❌ MAUVAIS — `env` révèle toutes les propriétés, y compris les secrets management: endpoints: web: exposure: include: "*"

En production :

# ✅ BON — expose uniquement les endpoints non sensibles management: endpoints: web: exposure: include: health,info,prometheus

2. show-details: always révèle trop d’informations

show-details: always dans /actuator/health révèle les détails de chaque composant (taille disque, pilote de base de données, …). En production, utiliser when-authorized pour masquer les détails aux utilisateurs non-admin.

3. Endpoint httptrace absent en WebFlux

httptrace repose sur HttpTraceRepository qui n’existe pas dans un projet WebFlux. La section /actuator/httptrace renvoie alors 404. Utiliser WebHttpTraceRepository à la place, ou se tourner vers un outil externe (Prometheus) pour le tracing.

4. Annoter un HealthIndicator avec @LivenessIndicator / @ReadinessIndicator

Depuis Spring Boot 3.4, on peut préciser à quelle sonde un HealthIndicator participe :

@Component @LivenessIndicator public class CacheHealthIndicator implements HealthIndicator { ... }

Sans annotation, un HealthIndicator participe à la fois à liveness et readiness. Cela ne peut pas servir à déclencher le shutdown — seul @PreDestroy garantit un arrêt contrôlé (déconnecter le pool JDBC, arrêter le consommateur Kafka, etc.).

5. Oublier le port management

Par défaut, Actuator partage le port HTTP de l’application (8080). Pour séparer le monitoring du trafic métier :

management: server: port: 8081 endpoints: web: base-path: /actuator

L’application écoute sur 8080, le monitoring sur 8081. Utile pour ne pas exposer /actuator au load balancer principal.

Checklist de mise en production

  • Starter spring-boot-starter-actuator ajouté
  • management.endpoints.web.exposure.include limité à health,info,prometheus
  • Spring Security configure l’accès : health/info publics, reste restreint
  • Sonde liveness/readiness activée (management.endpoint.health.probes.enabled=true)
  • Suppression des champs sensibles (show-details: when-authorized)
  • Port management distinct (management.server.port) si souhaité
  • HealthIndicator personnalisée pour les dépendances externes critiques
  • Monitoring Grafana/Prometheus connecté à /actuator/prometheus