쿠버네티스(Kubernetes) 1.37 이 지난 2026년 8월 26일에 릴리즈됐다. 간단히 바뀐 것에 대해서 알아 본다.
cgroup v1 영구 퇴출
이제 cgroup v1 이 영구 퇴출 됐다. 이 환경에서 kubelet 을 구동하면 ‘Refuse to Start’ 메시지를 보게 된다. 이 제약 조건은 결국 리눅스 OS 배포판 최소버전을 정의하게 된다. 쿠버네티스 1.37 을 쓰기 위한 최소 리눅스 배포판은 다음과 같다.
- RHEL 9.x 이상
- Ubuntu 22.04 LTS 이상
RHEL 8 에서도 사용이 가능하지만, 커널 패치를 하면 가능해 지지만 커널 패치라는게 아무나 가능하지 않다. 그래서 RHEL 9를 쓰는게 마음편하다.
RHEL 7 은 답이 없다.
kube-dns 지원 중단
이제 더 이상 kube-dns 를 지원하지 않는다. kube-dns 는 초창기 Go와 SkyDNS 라이브러리를 조합해 만들어졌지만, 확장성, 성능, 플러그인 생태계 측면에서 고성능으로 재작성된 C 기반/Go 플러그인 구조의 CoreDNS 에 비해 한계가 명확했다.
이제는 CoreDNS 를 권장하는데, CNCF 를 졸업한 프로젝트이기도 하다.
Pod certificates
Pod 를 위한 인증서 발급한 기능이다. X.509 인증서를 podCertificate 를 통해서 볼륨 투영(projected volume)을 통해서 받을 수 있고, 자동으로 로테이션과 프로비전을 해준다.
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 |
apiVersion: v1 kind: Pod metadata: name: my-app spec: containers: - name: app image: nginx:latest volumeMounts: - name: web-cert mountPath: /var/run/secrets/certs readOnly: true volumes: - name: web-cert projected: sources: - podCertificate: signerName: "kubernetes.io/kube-apiserver-client" expirationSeconds: 3600 |
볼륨 투영은 기존의 볼륨 마운트(Volume mount) 를 하나의 마운트 볼륨에 여러개의 객체를 하나로 투영해서 마운트를 해주는 기능이다. 예를들면 다음과 같다.
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 |
volumeMounts: [{ mountPath: "/var/run/secrets/kubernetes.io/serviceaccount", name: "kube-api-access-5fc62", readOnly: true, }], .... .... volumes: [{ name: "kube-api-access-5fc62", projected: { defaultMode: 420, sources: [{ serviceAccountToken: { expirationSeconds: 3607, path: "token", }, }, { configMap: { items: [{ key: "ca.crt", path: "ca.crt", }], name: "kube-root-ca.crt", }, }, { downwardAPI: { items: [{ fieldRef: { apiVersion: "v1", fieldPath: "metadata.namespace", }, path: "namespace", }], }, }], }, }], |
‘/var/run/secrets/kubernetes.io/serviceaccount‘ 에 serviceAccountToken, configMap, downwardAPI 세개에 객체에 파일을 마운트 해준다.
ClusterTrustBundles – Certificate Trust Management
Root CA(최상위 인증기관) 및 신뢰할 수 있는 CA 인증서 목록을 클러스터 전역에서 관리하고 배포하는 기능이다. ClusterTrustBundles 는 클러스터 전역(Clouster-scoped)에서 X.509 신뢰 앵커(Trust Anchors, 즉 Root 및 중간 CA 인증서)들을 표준화된 쿠버네티스 API 객체로 안전하게 담아두는 곳이다.
예전에는 여러 네임스페이스에 흩어져 있는 파드들이 특정 사내 Root CA나 서비스 메시(예: Istio 등)의 인증서를 신뢰하게 만들려면, 관리자가 일일이 ConfigMap이나 Secret을 만들고 각 네임스페이스마다 복사해서 동기화해야 했다. 거기다 RootCA 를 주기적으로 교체(Rotation)할 때는 구버전 인증서와 신버전 인증서를 일정 기간 동안 동시에 신뢰하도록 만들어야 하는데, 이를 수동으로 관리하기가 매우 까다로웠다.
이런 지옥같은 일을 구해낸게 ClusterTrustBundle 이다. 이것을 사용하면 쿠버네티스 API 레벨에서 선언적(Declarative)으로 Root CA 번들을 관리할 수 있고, 파드들이 이 번들을 볼륨(Projected Volume)으로 아주 쉽게 가져다 쓸 수 있게 됐다 .ClusterTrustBundle은 클러스터 전역에 딱 하나(또는 인증서 그룹별로)만 생성해 두면, 어떤 네임스페이스에 있는 파드든 상관없이 이 번들을 자유롭게 가져다 쓸 수 있다.
클러스터 전역이기 때문에 읽기 접근(Read Access)은 클러스터 내의 모든 서비스 계정(ServiceAccount)과 파드는 기본적으로 읽기 권한을 가진다. 파드가 구동될 때 인증서를 마운트해야 하기 때문이다. 하지만 쓰기/수정(Create/Update)는 아무나 Root CA 정보를 등록하거나 바꿀 수 없도록 ClusterTrustBundle을 생성하거나 수정하려면 클러스터 레벨의 엄격한 권한(Signer 권한 등)이 필요하도록 설계되었다.
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 |
apiVersion: v1 kind: Pod metadata: name: my-app-pod spec: containers: - name: app image: my-app:latest volumeMounts: - name: my-trust-vol mountPath: /etc/ssl/certs-cluster # ① 컨테이너 안에서 이 폴더에 볼륨을 통째로 마운트! volumes: - name: my-trust-vol projected: sources: - clusterTrustBundle: name: "example.com:my-signer" path: "ca.crt" # ② mountPath(/etc/ssl/certs-cluster) 안에서 이 파일 이름으로 저장됨 |
KYAML – Kubernetes YAML
쿠버네티스 환경에서 기존 YAML이 가진 모호함과 불편함을 덜어내기 위해 다듬어진 안전한 YAML 하위 집합(Subset) 규격이다. 이걸 만든 이유는 기존의 YAML 이 가진 고질적인 문제점 때문이였다.
- 들여쓰기 민감성: 공백 한 칸만 어긋나도 구조가 완전히 깨지거나 파싱 에러가 남.
- 암묵적 타입 변환 (Type Coercion): 예를 들어 노르웨이 국가 코드인
NO나 버전 번호 같은 것들이 YAML 파서에 의해 자동으로 불리언(false)이나 다른 타입으로 오인되어 해석되는 참사(일명 The Norway Bug)가 발생하곤 했음. - JSON과의 괴리: JSON은 기계가 다루긴 좋지만 주석을 지원하지 않고 따옴표나 쉼표가 너무 엄격함.
이와같은 문제를 해결하고자 KYAML 이 만들어 졌다. 주요한 특징은 다음과 같다.
- 명시적인 구조: 들여쓰기 공백에만 의존하지 않고 중괄호(
{})나 대괄호([]) 같은 구조적 표현을 적극 활용하고, 문자열을 큰따옴표로 확실하게 감싸 타입 오인식을 방지 - 호환성: KYAML로 작성된 파일은 여전히 완벽한 유효 YAML이기 때문에 기존 쿠버네티스 API 서버나 ‘
kubectl apply‘에 그대로 넣어도 아무 문제 없이 동작한다. - 사용법: ‘
kubectl get ... -o kyaml‘ 같은 식으로 출력을 뽑아낼 때 활용할 수 있으며, 특히 CI/CD 파이프라인이나 스크립트에서 매니페스트 값을 코드로 조작(Patch)할 때 들여쓰기 깨짐 사고를 획기적으로 줄여줌.
다음과 같이 확인할 수 있다.
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 |
$ kubectl get pod hello-6dd6df4c59-hwqdg -o kyaml --- { apiVersion: "v1", kind: "Pod", metadata: { annotations: { cni.projectcalico.org/containerID: "d6164cf4d7495cf6463b9eb847b2e0e5c2595f79f45053030a70e64b74fa718e", cni.projectcalico.org/podIP: "10.31.20.53/32", cni.projectcalico.org/podIPs: "10.31.20.53/32", kubectl.kubernetes.io/restartedAt: "2026-09-17T17:19:37Z", }, creationTimestamp: "2026-09-18T13:44:05Z", generateName: "hello-6dd6df4c59-", generation: 1, labels: { app: "hello", pod-template-hash: "6dd6df4c59", tier: "backend", track: "stable", }, name: "hello-6dd6df4c59-hwqdg", namespace: "default", ownerReferences: [{ apiVersion: "apps/v1", blockOwnerDeletion: true, controller: true, kind: "ReplicaSet", name: "hello-6dd6df4c59", uid: "f35a0611-6587-44b0-bd2c-692ae55a2aec", }], resourceVersion: "2491867", uid: "bc2e829e-2003-4219-b723-44da7d503a03", }, |
[,{ 가 많이 나온다.