LabHub

CKAD — 쿠버네티스 애플리케이션 개발자 · 애플리케이션 환경·설정·보안 · 실습

securityContext, 리소스, 쿼터, QoS

LabHub 에서 이어서 보기

목표

파드가 노드에서 무엇을 할 수 있는지(securityContext, ServiceAccount)와 얼마를 쓸 수 있는지(resources, LimitRange, ResourceQuota)를 매니페스트로 정하고, 그 결과 QoS 클래스가 어떻게 결정되는지 확인할 수 있게 된다.

왜 중요한가

컨테이너는 기본적으로 root 로 돈다. 이미지가 그렇게 만들어졌기 때문이다. 컨테이너 탈출 취약점이 하나라도 있으면 그 root 가 노드의 root 로 이어질 수 있다. runAsNonRoot: true 는 UID 0 으로 뜨려는 컨테이너를 아예 시작시키지 않고, capabilities.drop: ["ALL"] 은 커널이 주는 특권을 전부 회수한다. 웹 서버가 80 포트를 열어야 한다면 NET_BIND_SERVICE 하나만 다시 더한다. 이것이 최소 권한 원칙의 구체적인 모습이다.

리소스 쪽은 두 층으로 이해한다. requests 는 스케줄러의 언어다. 노드에 남은 할당 가능량이 requests 합계보다 커야 파드가 얹힌다. 실제 사용량과는 무관하다. limits 는 노드의 언어다. CPU 는 cgroup 쿼터로 스로틀링되고 메모리는 넘는 순간 OOMKilled 된다. 그래서 메모리 limits 를 실제 피크보다 낮게 잡으면 파드가 조용히 반복 재시작한다.

LimitRange 와 ResourceQuota 는 반드시 세트로 이해해야 한다. 쿼터가 걸린 네임스페이스에 requests/limits 없는 파드를 만들면 생성 자체가 거부된다. 팀 네임스페이스에 쿼터만 걸어 두면 아무것도 안 뜨는 사고가 나므로, LimitRange 로 기본값을 채워 주는 것이 사실상 필수다.

단계

1. 네임스페이스 ckad-secure 를 만들고 그 안에 ServiceAccount app-sa 를 만든다.
2. 파드 sa-pod 를 만든다. 이미지 nginx:1.27, serviceAccountName: app-sa, automountServiceAccountToken: false.
3. 파드 nonroot 를 만든다. 이미지 nginx:1.27, 파드 수준 securityContextrunAsNonRoot: true, runAsUser: 1000, fsGroup: 2000.
4. 파드 hardened 를 만든다. 이미지 nginx:1.27, 컨테이너 이름 app, 컨테이너 수준 securityContextallowPrivilegeEscalation: false, readOnlyRootFilesystem: true, capabilities.drop: ["ALL"], capabilities.add: ["NET_BIND_SERVICE"].
5. Deployment api 를 만든다. 레플리카 2, 라벨 app=api, 이미지 nginx:1.27, 컨테이너 resources.requestscpu: 100m / memory: 128Mi, resources.limitscpu: 500m / memory: 512Mi.
6. LimitRange defaults 를 만든다. type: Containerdefault(limits) cpu: 200m / memory: 256Mi, defaultRequest cpu: 100m / memory: 128Mi, max cpu: "1" / memory: 1Gi, min cpu: 50m / memory: 64Mi.
7. ResourceQuota team-quota 를 만든다. requests.cpu: "2", requests.memory: 4Gi, limits.cpu: "4", limits.memory: 8Gi, pods: "10".
8. 파드 두 개를 더 만든다. qos-guaranteed 는 requests 와 limits 가 모두 cpu: 250m / memory: 256Mi 로 같아야 하고, qos-burstable 은 requests 만 cpu: 100m / memory: 128Mi 로 준다. 둘 다 이미지 nginx:1.27.

참고

단계 8개

  1. 네임스페이스와 ServiceAccount
  2. 파드에 ServiceAccount 지정하고 토큰 자동 마운트 끄기
  3. 파드 수준 securityContext
  4. 컨테이너 수준 securityContext 와 capabilities
  5. Deployment 에 requests 와 limits 지정
  6. LimitRange 로 기본값과 상하한 정하기
  7. ResourceQuota 로 네임스페이스 총량 제한
  8. QoS 클래스를 의도한 대로 만들기 (종합)