쿠버네티스에는 파드가 정상인지를 판단하기 위한 헬스체크 기능이 있다.
파드 내부 컨테이너에서 실행 중인 프로세스가 동작하고 있는지에 대한 헬스 체크는 쿠버네티스가 표준으로 하고 있으며, 이상 종료된 경우 파드에 설정된 spec.restartPolicy에 따라 파드를 재시작한다.
이외에도 상세한 조건으로 헬스체크를 할 수 있다.
헬스체크는 컨테이너별로 이루어지며, 어느 하나의 컨테이너라도 실패하면 전체 파드가 실패한 것으로 간주한다.
livenessProbe:
exec:
command: ["test", "-e", "/ok.txt"]
livenessProbe:
httpGet:
path: /health
port: 80
scheme: HTTP
host: web.example.com
httpHeaders:
- name: Authorization
value: Bearer TOKEN
livenessProbe:
tcpSocket:
port: 80
- gRPC 헬스체크
gRPC를 사용한 애플리케이션에서 헬스 체크를 하는 경우 httpGet으로 체크하기 위해 별도 HTTP 엔드포인트를 준비하거나 tcpSocket으로 포트 활성화만 체크할 수도 있는데, 이러한 방법은 헬스 체크의 정확도가 낮다.
해결 방법은 다음과 같다.
gRPC에는 원래 gRPC Health Checking Protocol 을 사용한 헬스 체크 기능이 있으며, grpc_health_probe를 사용하면 엔드포인트에 대한 헬스 체크를 할 수 있다.
exec.command 에서 실행하기 위해 사전에 컨테이너 이미지에 grpc_health_probe 바이너리를 추가해 두어야 한다.
예)
livenessProbe:
exec:
command: ["/bin/grpc_health_probe", "-addr=:5000"]
설정 항목 | 내용 | 기본 값 |
---|---|---|
initialDelaySeconds | 첫 번째 헬스 체크 시작까지의 지연(최대 failureThreshold 만큼 연장) | 0 |
periodSeconds | 헬스 체크 간격 시간(초) | 10 |
timeoutSeconds | 타임아웃까지의 시간(초) | 1 |
successThreshold | 성공이라고 판단하기까지의 체크 횟수 | 1 |
failureThreshold | 실패라고 판단하기까지의 체크 횟수 | 3 |
livenessProbe:
initialDelaySeconds: 5
periodSeconds: 5
timeoutSeconds: 1
successThreshold: 1
failureThreshold: 1
Liveness Probe, Readiness Probe, Startup Probe 모두 위 나타난 다섯가지 헬스 체크 간격에 대해 파라미터 설정이 가능하다.
헬스 체크 방법 3가지와, 헬스 체크 방식 3가지로 총 9가지 패턴의 헬스 체크를 생성할 수 있다.
아래 예제에서는 Liveness Probe로 http://localhost:80/index.html 에 HTTP GET 요청을 체크하고, Readiness Probe로 /usr/share/nginx/html/50x.html 파일이 있는지 확인한다.
apiVersion: apps/v1
kind: Deployment
metadata:
name: nginx-healthcheck
spec:
selector:
matchLabels:
app: nginx
template:
metadata:
labels:
app: nginx
spec:
containers:
- name: nginx
image: nginx:latest
# command: ["/bin/bash", "-c", "--"]
# args: ["while true; do sleep 30; done;"]
ports:
- containerPort: 80
livenessProbe:
httpGet:
path: /index.html
port: 80
scheme: HTTP
timeoutSeconds: 1
successThreshold: 1
failureThreshold: 2
initialDelaySeconds: 5
periodSeconds: 3
readinessProbe:
exec:
command: ["ls", "/usr/share/nginx/html/50x.html"]
timeoutSeconds: 1
successThreshold: 2
failureThreshold: 1
initialDelaySeconds: 5
periodSeconds: 3
설정은 kubectl describe 등에서 확인할 수 있디.
# pod 에 설정된 probe 확인
$ k describe pod nginx-healthcheck | egrep -E "Liveness|Readiness"
Liveness: http-get http://:80/index.html delay=5s timeout=1s period=3s #success=1 #failure=2
Readiness: exec [ls /usr/share/nginx/html/50x.html] delay=5s timeout=1s period=3s #success=2 #failure=1
# index.html 삭제
$ k exec -it nginx-healthcheck -- rm -f /usr/share/nginx/html/index.html
# --watch 옵션을 사용하여 파드 상태 변화를 확인
$ k get pods nginx-healthcheck --watch
NAME READY STATUS RESTARTS AGE
nginx-healthcheck 1/1 Running 0 37s
nginx-healthcheck 0/1 Running 1 71s
nginx-healthcheck 1/1 Running 1 77s
Liveness Probe가 실패한 경우 파드의 restartPolicy(기본값 Always)에 따라 컨테이너를 재시작한다.
그래서 Restart 카운트가 증가하는 것을 확인할 수 있다.
이번에는 Readiness Probe를 실패시켜 보자. 다음 예제에서는 /usr/share/nginx/html/50x.html 파일이 있는지 명령어 기반으로 체크하고 있다.
체크가 실패하도록 해당 파일을 삭제하고 다시 생성하여 동작을 확인한다.
# 50x.html 삭제
$ k exec -it nginx-healthcheck -- rm -f /usr/share/nginx/html/50x.html
# 확인
$ k get pods nginx-healthcheck--watch
NAME READY STATUS RESTARTS AGE
nginx-healthcheck 1/1 Running 0 21s
nginx-healthcheck 0/1 Running 0 42s
Readiness Probe가 실패한 경우 READY 상태가 아니므로, 서비스에서 트래픽 전송을 차단한다.
또한, Liveness Probe와는 달리 컨테이너가 재시작되지 않는다.
안녕하세요 : )
정리해 주신 글 잘 읽었습니다.
1. Liveness Probe랑 2. Readiness Probe 동작 설명하는 사진이 둘 다 Readiness네요
수고하세요~!