Kubernetes로 애플리케이션을 배포하다 보면
yaml 파일 방식으로 여러 설정값을 적용하여 배포하는데,
오늘은 그 중에서 Resourse Request와 Limit에 대해서 정리해보고자 한다.
k8s에서 Resource Request와 Limit은 컨테이너에 할당되는 CPU와 Memory 자원량을 나타내며
CPU는 Milicore단위(1,000 Milicore = 1 Core)로 Memory는 Mbyte단위로 할당된다.
Request량은 k8s의 Pod 스케쥴링의 기준이다.
k8s의 Pod는 하나 이상의 컨테이너로 구성됨으로 실제 Request량은 Pod의 모든 컨테이너 Request량을 합친 값이 된다.
Pod 스케쥴링이란 Pod를 어떤 Node에 배치하는가를 결정하는 과정으로 k8s는 Round-Robin방식으로 수행한다.
즉, 첫 번째 Node가 요청되는 Pod Request량을 수용할 자원을 가지고 있다면 배치(생성)를 하고 만약 그렇지 않다면
다음 차례의 Node에 대해 동일한 작업을 수행하는 방식이다.
만약 모든 Node가 Pod Request량을 수용 할 수 없으면
Pod는 Pending상태로 되며 Pod 스케쥴링을 할 수 없다는 Event가 발생된다.
단, 노드를 지정하여 Pod를 배치하는 경우는 해당 노드에 대해서만 스케쥴링을 수행한다.
Limit량은 Pod가 사용하는 자원을 제한한다. 즉 Pod는 Limit량 이상의 자원을 사용할 수 없다.
만약 Limit량 이상을 사용한다면 Pod는 비 정상 동작을 할 것이고 최악의 경우 오류와 함께 종료될 수 도 있다.
Liveness Pobe를 설정하였다면 k8s가 Pod가 비정상임을 알고 Restart정책에 따라 재시작 또는 재배치(스케쥴링)를 수행한다.
즉 Limit 량은 Request량보다 반드시 같거나 커야 한다.
그렇다면
Request량을 초과 사용하면 어떻게 되는가?
Pod가 Request량을 초과하여 사용해도 Limit량을 넘지 않으면 문제는 없다.
다만 Node의 자원이 부족할 경우에는 Request량을 초과 한 Pod는 퇴거(Eviction)의 대상이 된다.
K8s는 Node 자원 부족 시(예:Out of memory) Request량을 초과한 Pod부터 종료를(Terminate) 수행한다.
이렇게 하는 이유는 자원이 부족한 노드에서 다른 노드로 재배치를 수행하기 위함이다.
만약 모든 Node가 자원이 부족하다면 이 Pod는 Pending상태로 지속된다.
따라서 서비스 운영 시 자원의 부족에 따른 Pod의 재배치 또는 Pending상태에 대비하여
복제(Replication)를 설정하거나 주요한 Pod를 특정 Node에 한정하여 배치하는 것을 고려해야 한다.
Limit량을 초과하여 사용하면 어떻게 되는가?
Pod가 Limit량을 초과하게 되면 overcommitted 상태가 된다.
이 상태에서 CPU는 throttling을 통해 압축 조정된다.
하지만 Memory의 경우 앞서 설명한 것처럼 Pod는 이상 동작을 보일 수 있고, Node자원 부족 시 퇴거 대상이 된다.
- Request와 Limit량 산정은 어떻게 해야 하는가?
사실 용량 산정이 그렇듯이 이 것에 대한 정답은 없다.
하지만 Request는 평균 사용량+10%로
Limit은 Peek 사용량 중 최대 사용량을(비 정상 Peek 제외) 기준으로 설정하는 것을 권장한다.
이 경우 사용량은 대부분 Request 이하가 될 것이고
특정 Peek시 에는 Request-Limit구간을 보여 안정된 자원관리를 할 수 있다.
만약 Peek가 장시간 지속되는 경우가 있다면 Pod Scaling을 설정하여 자동으로 스케일링을 하도록 한다.
- Request와 Limit량을 설정하지 않으면 어떻게 되는가?
개발 중에는 자원량을 설정하지 않아도 문제는 없다.
Request와 Limit량을 설정하지 않으면 Node의 자원 전체를 사용할 수 있다는 의미와 같다.
하지만 운영 시에는 Request량이 설정되어 있지 않으면 k8s는 Node자원을 기준으로 정확한 스케쥴링을 수행하지 못한다.
즉 한 Node에 Pod가 초과 배치될 수 있고, Node자원 부족시 퇴거 대상이 많아지는 경우가 발생한다.
Request량이 설정되지 않은 Pod는 요청량을 초과 사용하고 있다고 k8s가 판단하기 때문이다.
Limit량의 경우도 마찬가지로 Node자원 부족시 퇴거 우선순위가 된다
- Request와 Limit량은 컨테이너에만 설정하는가?
Request와 Limit량은 네임스페이스(Namespace)에 설정할 수 있다.
이를 ResourceQutoas라고 하는데 이 경우에는 네임스페이스 안의 Pod들이 ResourceQutoa를 초과할 수 없도록 제한한다.
주로 운영 서비스에 적용하는데 한정된 Node(클러스터) 자원 안에서
타 서비스의 자원 사용에 영향을 주지 않도록 한정할 때 사용한다.
LimitRange라는 것도 있는데 이는 기본(default)과 Max/Min에 해당하는 Request와 Limit량을 네임스페이스에 설정하여
그 안의 Pod의 Request와 Limit량의 범위를 한정하는 데 사용한다.
기본 값은 Request와 Limit량을 설정하지 않은 Pod에 적용되고
Max/Min은 Pod에 설정한 Request와 Limit량에 최대/최소 범위를 한정하는 데 사용한다.
예전에 정리한 내용을 리마인드 하면서 정리를 해보았다.
그저
어렵다.

'Infra & Network > Kubernetes' 카테고리의 다른 글
Kubernetes Package 툴 Helm 으로 Deploy Rollback 시키기 (0) | 2022.05.27 |
---|