Kubernetes Pod의 Resource 제한 (request, limit)

woogi·2024년 1월 24일
0
post-thumbnail

Kubernetes Pod의 Resource 제한(request, limit)

kubernetes는 파드 및 컨테이너의 리소스에 대해서 request와 limit 설정으로 컨테이너에 할당 되는 CPU와 Memory 자원량을 제한 할수 있다.

동작 방식

  • 파드의 컨테이너에 대한 리소스 request, limit을 지정
  • kube-scheduler가 해당 설정 정보를 사용하여 파드를 배치할 노드를 결정
  • kubelet은 컨테이너에 설정한 Resource 제한을 넘지 않도록 관리

설정 yaml

    resources:
      limits:
        cpu: "1"
        memory: 1Gi
      requests:
        cpu: "1"
        memory: 1Gi
  • spec.containers[].resources.limits.cpu
  • spec.containers[].resources.limits.memory
  • spec.containers[].resources.requests.cpu
  • spec.containers[].resources.requests.memory

CPU 자원 단위

Millicores단위로 표시된다.
1 Core = 1000m
0.1 Core= 100m

Memory 자원 단위

바이트 단위로 표시된다.
Ki = 킬로바이트
Mi = 메가바이트
Gi = 기가바이트


그럼 구체적으로 request와 limit 설정에 대해 자세히 알아보자


request & limit

request

파드를 실행하기 위한 최소 리소스 양으로, 노드에 남아있는 리소스가 request보다 적으면 해당 노드에 스케줄링이 되지 않는다.
(스케줄링 가능한 모든 노드의 리소스가 부족하면 pending 상태로 어디에도 스케줄링이 되지 않는다.)
스케줄링 된 노드에 cpu, memory가 남아있다면 지정된 것보다 더 많은 리소스를 사용할 수 있다.(허용됨)

request를 특정값으로 설정했다고 파드에 그 값으로 할당된다는것은 아니고 어느 노드에 스케줄링 될지에 사용하는 값이다.

limit

파드가 실행될 때 사용할 수 있는 최대 리소스의 양으로, limit 값이 설정된 파드는 cpu, memory 사용량이 limit 값을 넘어설 수 없다.


파드가 request, limit 설정값을 초과 했을 경우는 어떻게 되나?


request 설정 값 초과의 경우

파드는 CPU, Memory 모두 Request량을 초과해서 사용이 가능하기 때문에 컨테이너가 실행되다 보면 자원부족으로 request 설정값에서 limit 값까지 계속해서 리소스를 요청하게 된다.
노드에서 실행 중인 모든 파드에 대한 Request 리소스의 합계가 해당 노드의 물리적 용량을 초과되는 상태를 overcommitted 상태라고 하는데, overcommitted 상태에서 request 설정에 따라 아래와같이 동작한다.

CPU

overcommitted 상태가 되면 CPU는 압축 가능한 리소스이기 때문에 컨테이너가 종료되지는 않는다.
다만, CPU request 설정 값 까지 강제적으로 줄여서 리소스 부족을 해결한다. 때문에 CPU throttling 현상이 발생한다.

해당 문제를 예방하기 위해서는 request와 limit의 설정값을 동일하게 설정 하면 throttling은 발생하지 않겠지만, 부하 테스트 및 실제 운영중인 서비스라면 일정 기간 동안의 리소스 사용량 추이를 확인하여 컨테이너가 사용하는 적절한 리소스량을 설정 하는것이 중요하다.

압축 가능한 리소스 (compressible resource)
리소스의 사용량이 최대일 때 해당 리소스를 요구 하는 프로세스가 사용 가능해질 때까지 기다려야 함을 의미한다. 즉, 프로세스를 제한한다. (CPU, 네트워크대역폭과 같은 리소스가 있다)

CPU throttling
프로세스가 특정 리소스 제한에 도달하려고 시도 할 때 속도가 느려지는 동작을 의미한다.
즉, CPU 사용량이 100%인 경우 CPU가 필요한 프로세스는 CPU 시간을 받을 때까지 기다려야 함

Memory

overcommitted 상태가 되면 Memory는 압축 불가능한 리소스이기 때문에 클러스터는 리소스를 수거하기 위해 파드를 우선순위에 따라서 퇴거(Eviction)시킨다.
우선 순위는 PodPriority 등의 여러 우선 순위 선발 로직이 있는데 대체적으로 request에 비해서 오버된 양이 가장 큰 파드를 우선적으로 삭제한다.

Kubelet이 Pod eviction을 수행하기도 전에 갑작스럽게 메모리 사용량이 늘면 OOM killer는 메모리 부족으로 인해 시스템이 불안정해지는 것을 방지하기 위해 파드를 죽일수 있다.

압축 불가능한 리소스 (incompressible resource)
리소스가 부족하면 프로세스가 이를 기다릴 수 없다는것을 의미, 실행할 수 없으므로 문제가 생긴다.(Memory, Storage 같은 리소스가 있다)

OOM Killer
Out Of Memory Killer 의 약자로 메모리가 부족할 경우 특정 프로세스를 강제로 종료시킨다.
이는 리눅스 운영 체제의 커널 기능 중 하나로, 메모리 부족으로 인해 시스템이 불안정해지는 것을 방지하기 위해 동작한다.
kubernetes 관점에서는 cgroup에 의해 limit이 설정되고 oom killer가 임계치를 넘었을때 프로세스를 kill 시킨다.


limit 설정 값 초과의 경우

limit 값이 설정된 파드는 CPU, Memory 사용량이 limit 값을 넘어설 수 없기 때문에 아래와 같이 동작한다.

CPU

앞서 설명했듯이 컨테이너가 종료되지는 않지만, CPU throttling 현상으로 느려진다.

Memory

limit 값을 넘어설 수 없기에 파드는 OOM Killed된다.

참고

https://medium.com/directeam/kubernetes-resources-under-the-hood-part-1-4f2400b6bb96
https://bcho.tistory.com/1347
https://kubernetes.io/ko/docs/concepts/configuration/manage-resources-containers/
https://itchain.wordpress.com/2018/05/16/kubernetes-resource-request-limit/

0개의 댓글

관련 채용 정보