StatefulSet 파드 강제 삭제
StatefulSet 파드 강제 삭제 (Force Delete StatefulSet Pods)
이 페이지는 stateful set의 일부인 파드를 삭제하는 방법을 보여주고, 그렇게 할 때 유의해야 할 고려 사항을 설명해요.
출처: 문서
본문
시작하기 전에 (Before you begin)
- 이는 상당히 고급 작업이며 StatefulSet에 내재된 일부 속성을 위반할 가능성이 있어요.
- 진행하기 전에 아래 열거된 고려 사항에 익숙해져요.
StatefulSet 고려 사항
StatefulSet의 정상적인 운영에서 StatefulSet 파드를 강제 삭제할 필요는 결코 없어요. StatefulSet 컨트롤러는 StatefulSet의 구성원을 생성·확장·삭제하는 책임을 져요. 서수 0부터 N-1까지의 지정된 수의 파드가 살아 있고 준비 상태임을 보장하려 해요. StatefulSet은 어떤 시점에도 주어진 정체성(identity)을 가진 파드가 클러스터에 최대 한 개만 실행되도록 보장해요. 이를 StatefulSet이 제공하는 최대 하나(at most one) 의미론이라고 해요.
수동 강제 삭제는 StatefulSet에 내재된 최대 하나 의미론을 위반할 가능성이 있으므로 주의해서 수행해야 해요. StatefulSet은 안정적인 네트워크 정체성과 안정적인 저장소가 필요한 분산·클러스터 애플리케이션을 실행하는 데 사용될 수 있어요. 이런 애플리케이션은 종종 고정된 수의 멤버가 고정된 정체성을 가진 앙상블(ensemble)에 의존하는 구성을 가지게 돼요. 같은 정체성을 가진 여러 멤버가 있으면 재앙적일 수 있고 데이터 손실로 이어질 수 있어요(예: 쿼럼 기반 시스템에서의 split brain 시나리오).
파드 삭제하기
다음 명령으로 파드를 정상적으로(graceful) 삭제할 수 있어요:
kubectl delete pods <pod>
위가 정상적인 종료로 이어지려면 파드 반드시 pod.Spec.TerminationGracePeriodSeconds 를 0으로 지정하지 않아야 해요. pod.Spec.TerminationGracePeriodSeconds 를 0으로 설정하는 관행은 안전하지 않고 StatefulSet 파드에 대해 강력히 권장되지 않아요. 정상 삭제는 안전하며 kubelet이 apiserver에서 이름을 삭제하기 전에 파드가 정상적으로 종료되도록 보장해요.
노드에 도달할 수 없게 되어도 파드는 자동으로 삭제되지 않아요. 도달할 수 없는 노드에서 실행 중인 파드는 시간 초과 후 'Terminating' 또는 'Unknown' 상태로 들어가요. 사용자가 도달할 수 없는 노드의 파드를 정상 삭제하려 할 때에도 파드가 이런 상태로 들어갈 수 있어요.
이런 상태의 파드를 apiserver에서 제거할 수 있는 유일한 방법은 다음과 같아요:
- Node 객체가 삭제되는 경우(사용자가 직접 또는 Node 컨트롤러에 의해)
- 응답하지 않는 노드의 kubelet이 응답을 시작해 파드를 죽이고 apiserver에서 항목을 제거하는 경우
- 사용자가 파드를 강제 삭제하는 경우
권장되는 모범 사례는 첫 번째 또는 두 번째 방식을 사용하는 것이에요. 노드가 확실히 죽었다면(예: 영구적으로 네트워크에서 분리됨, 전원 꺼짐 등) Node 객체를 삭제해요. 노드가 네트워크 파티션을 겪고 있다면 이를 해결하려 하거나 해결되기를 기다려요. 파티션이 복구되면 kubelet이 파드 삭제를 완료하고 apiserver에서 이름을 해제해요.
일반적으로 파드가 노드에서 더 이상 실행되지 않거나 관리자가 노드를 삭제하면 시스템이 삭제를 완료해요. 파드를 강제 삭제하면 이를 무시할 수 있어요.
강제 삭제 (Force Deletion)
강제 삭제는 파드가 kubelet으로부터 종료됐다는 확인을 기다리지 않아요. 강제 삭제가 파드를 죽이는 데 성공했는지와 무관하게, 즉시 apiserver에서 이름을 해제해요. 그러면 StatefulSet 컨트롤러가 같은 정체성으로 대체 파드를 만들 수 있게 되는데, 이는 여전히 실행 중인 파드의 복제로 이어질 수 있고, 그 파드가 여전히 StatefulSet의 다른 멤버와 통신할 수 있다면 StatefulSet이 보장하도록 설계된 최대 하나 의미론을 위반하게 돼요.
StatefulSet 파드를 강제 삭제할 때, 해당 파드가 결코 다시 StatefulSet의 다른 파드와 접촉하지 않을 것이며 그 이름을 안전하게 해제해 대체 파드를 만들 수 있다고 단언하는 것이에요.
kubectl 버전 >= 1.5를 사용해 파드를 강제로 삭제하려면 다음을 수행해요:
kubectl delete pods <pod> --grace-period=0 --force
kubectl <= 1.4 버전을 사용한다면 --force 옵션을 생략하고 다음을 사용해야 해요:
kubectl delete pods <pod> --grace-period=0
이 명령 후에도 파드가 Unknown 상태에 걸려 있으면 다음 명령으로 클러스터에서 파드를 제거해요:
kubectl patch pod <pod> -p '{"metadata":{"finalizers":null}}'
StatefulSet 파드의 강제 삭제는 항상 관련 위험을 완전히 인지한 상태에서 주의 깊게 수행하세요.
더 알아보기 (Learn more)
StatefulSet 디버깅에 대해 더 알아보기