Spring Boot 커스텀 Health Check 구현
Spring Boot Actuator를 활용해 데이터베이스와 외부 API 상태를 반영하는 커스텀 Health Check를 구현하고 readiness와 liveness 엔드포인트로 그룹화하는 방법 설명서
목차
소개
애플리케이션의 가용성을 모니터링하려면 단순한 핑보다 더 정교한 상태 점검이 필요하다. Spring Boot Actuator는 기본 헬스 체킹 기능을 제공한다. 그러나 실제 환경에서는 데이터베이스 연결, 외부 API 응답, 큐 상태 등 서비스별 조건을 반영하는 커스텀 체크가 요구된다. 이 글은 spring boot health check custom, actuator health custom spring boot, spring boot readiness liveness 키워드를 염두에 두고 단계별로 구현 방법을 설명한다.
개념 정리: liveness vs readiness
두 개념은 컨테이너화된 환경에서 중요한 역할을 한다. 간단히 정리하면:
- Liveness: 애플리케이션이 다운되었는지 여부. 무한 루프나 치명적 오류 시 재시작을 유도.
- Readiness: 트래픽을 받아도 되는지 여부. 초기화나 외부 의존성이 준비되지 않았을 때는 트래픽 차단이 필요.
Spring Boot는 actuator 엔드포인트 그룹을 통해 readiness와 liveness를 분리해 관리할 수 있다.
준비: 의존성과 설정
Maven 의존성 추가
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-actuator</artifactId>
</dependency>
application.yml 예시
management:
endpoints:
web:
exposure:
include: health,info
endpoint:
health:
show-details: always
group:
readiness:
include: readinessProbe,db
liveness:
include: livenessProbe
위 설정에서 그룹은 포함할 헬스 인디케이터의 이름을 기준으로 묶는다. 이름은 빈(bean) 이름과 일치해야 한다.
커스텀 HealthIndicator 작성
HealthIndicator를 구현하면 Actuator의 /actuator/health에 상태를 추가할 수 있다. 아래 예시는 외부 API 응답을 확인하는 간단한 구현이다.
import org.springframework.boot.actuate.health.Health;
import org.springframework.boot.actuate.health.HealthIndicator;
import org.springframework.stereotype.Component;
@Component("readinessProbe")
public class ExternalApiHealthIndicator implements HealthIndicator {
@Override
public Health health() {
boolean apiUp = checkExternalApi();
if (apiUp) {
return Health.up().withDetail("externalApi", "reachable").build();
}
return Health.down().withDetail("externalApi", "unreachable").build();
}
private boolean checkExternalApi() {
// 간단한 HTTP 호출로 상태를 확인
return true; // 실제 호출 코드로 대체
}
}
@Component에 지정한 이름이 application.yml의 readiness 그룹 include 항목과 일치하면, 해당 체크는 readiness 엔드포인트의 결과에 포함된다.
데이터베이스 상태 확인 예
DB 연결 상태는 자주 사용하는 체크 항목이다. 다음은 JDBC 연결을 확인하는 예시이다.
import org.springframework.boot.actuate.health.Health;
import org.springframework.boot.actuate.health.HealthIndicator;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.stereotype.Component;
@Component("db")
public class DatabaseHealthIndicator implements HealthIndicator {
private final JdbcTemplate jdbcTemplate;
public DatabaseHealthIndicator(JdbcTemplate jdbcTemplate) {
this.jdbcTemplate = jdbcTemplate;
}
@Override
public Health health() {
try {
jdbcTemplate.queryForObject("SELECT 1", Integer.class);
return Health.up().withDetail("database", "reachable").build();
} catch (Exception ex) {
return Health.down(ex).withDetail("database", "unreachable").build();
}
}
}
엔드포인트 확인
구성 후에는 actuator 엔드포인트로 확인한다. 기본적으로 다음과 같이 접근한다.
curl http://localhost:8080/actuator/health
curl http://localhost:8080/actuator/health/readiness
curl http://localhost:8080/actuator/health/liveness
readiness와 liveness 그룹은 application.yml의 설정에 따라 포함된 체크만 반환한다. 운영에서는 인증과 네트워크 제한을 추가해 외부 노출을 최소화해야 한다.
운영 관점에서 고려사항
- 응답 지연 허용: 헬스 체크 자체가 과도한 리소스를 쓰지 않도록 타임아웃과 캐싱을 고려한다.
- 다중 체크 병렬화: 여러 종속성을 확인할 때는 병렬로 처리해 총 응답 시간을 줄인다.
- 민감 정보 노출 차단: show-details 설정을 운영 환경에 맞춰 제한한다.
- 모니터링 연동: 헬스 상태 변화를 알림이나 오케스트레이터와 연동한다.
마무리
기본 Actuator를 확장해 spring boot health check custom 요구사항을 충족할 수 있다. 커스텀 HealthIndicator를 이름으로 그룹에 포함하면 actuator health custom spring boot 방식으로 readiness와 liveness를 명확히 분리할 수 있다. 마지막으로 readiness/liveness 구분은 spring boot readiness liveness를 효과적으로 적용하는 핵심 개념으로, 배포와 오케스트레이션에서 큰 도움이 된다.