Kubernetes 1.26에서 Scheduling gates라는 새로운 파드 옵션이 도입되었습니다. 이 옵션은 파드를 Readiness 상태로 두어, 스케줄러는 해당 파드를 무시하며 궁극적으로 스케줄링 주기의 속도를 향상시킬 수 있습니다. 그렇다면 스케줄링 게이트란 무엇일까요? 먼저, 파드의 스케줄링 방식을 알아봅시다.
Pod 스케줄링
파드는 쿠버네티스에서 가장 작은 컴퓨팅 단위입니다. 프로젝트가 커지고 세분화될수록 파드의 수는 많아지는데요, 파드의 수가 방대해질수록 스케줄링의 중요도는 증가합니다. 스케줄링에 대해 알아보면, Node affinity 이나 Selector 를 사용하여 스케줄링 조건을 추가할 수 있지만 기본 방식은 FCFS 방식입니다.
하지만 스케줄링을 통해 노드가 결정되면 끝나지만 외부 이벤트를 통해 노드를 찾지 못해 스케줄링 프로세스가 계속 반복될 수 있습니다. 아래의 그림과 같이 파드가 생성되면 스케줄러는 지속적으로 적합한 노드를 찾습니다. 이런 과정은 노드를 찾거나 파드가 삭제될 때까지 계속 진행됩니다. 외부 이벤트로 차단된 파드와 같이 몇몇 파드는 오랜 기간 준비상태를 유지하며 스케줄링 사이클에 버려집니다. 이런 파드들로 인해 스케줄링 주기는 20ms 이상 걸릴 수 있고 스케줄링 성능에 큰 영향을 미치게 됩니다.
스케줄링 게이트는 이런 문제를 해결해 줄 수 있습니다.
- 기존
- Pod Scheduling Readiness
Scheduling gate
스케줄링 게이트는 새로 생성된 파드가 작동할 준비가 되지 않았음을 알리고 스케줄러는 이 파드를 무시하므로 불필요한 스케줄링 시도를 줄입니다. Cluster Autoscaler에서도 동일합니다. 이런 과정은 API 서버의 호출 없이 일어나, 부하를 유발하지 않습니다. 게이트를 지우는 것은 외부 컨트롤러가 합니다. 여러 스케줄링 게이트가 있다면 모두 삭제되어야 파드는 스케줄링 됩니다. 그렇다면, 스케줄링 게이트는 어떻게 사용할까요
사용방법
먼저, API 서버와 스케줄러에 먼저 스케줄링 게이트를 사용하기 위해서는 API 서버와 스케줄러의 feature gate PodSchedulingReadiness
옵션을 허용해야 합니다. 파드에서는 spec
부분에 schedulingGates
항목을 추가해야 합니다. API 서버와 스케줄러는 다음과 같이 기존의 .yaml
파일을 이용합니다.
- API server
spec:
containers:
- command:
- kube-apiserver
...
- --feature-gates=PodReadinessGates=true
- Scheduler
spec:
containers:
- command:
- kube-scheduler
...
- --feature-gates=PodReadinessGates=true
API 서버와 스케줄러는 작동 중인 환경에서 수동으로 바꿀 수 있으나 운영환경에서는 kubeadm의 도움을 받아 설정하는 것을 권장합니다.
- Pod
아래와 같이 파드의 .yaml
파일에서 스케줄링 게이트 필드를 추가하면 됩니다. 여 러 개를 추가할 수 있지만, 모든 항목이 제거되어야 다시 스케줄링 됩니다.
apiVersion: v1
kind: Pod
metadata:
name: test-pod
spec:
schedulingGates:
- name: foo
- name: bar
containers:
- name: pause
image: registry.k8s.io/pause:3.6
$kubectl get pod test-pod
NAME READY STATUS RESTARTS AGE
test-pod 0/1 SchedulingGated 0 7s
위의 명령어를 보면, kubectl get pod test-pod
를 통해 상태를 확인하여 파드가 SchedulingGated
상태로 작동되지 않은 것을 확인할 수 있습니다.
$kubectl get pod test-pod -o jsonpath='{.spec.schedulingGates}’
[{"name":"foo"},{"name":"bar"}]
현재 실행 중인 파드의 스케줄링 게이트 필드를 확인하고 싶다면 kubectl get pod test-pod -o jsonpath='{.spec.schedulingGates}’
명령어를 통해 내용을 확인할 수 있습니다.
관련 지표
아래의 명령어를 통해 지표를 확인할 수 있습니다.
$scheduler_pending_pods{queue="gated"}
10