Kubernetes 애플리케이션 배포에서 여러 YAML 파일을 관리하는 것은 번거롭다. Helm과 Kustomize는 이 문제를 해결하는 대표적인 도구이다. Helm은 패키지 관리자 방식으로, Kustomize는 오버레이 방식으로 설정을 관리한다.
Helm
Helm 개요
Helm은 Kubernetes의 패키지 관리자이다.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
| ┌─────────────────────────────────────────────┐
│ Helm │
├─────────────────────────────────────────────┤
│ Chart │
│ - Kubernetes 리소스들의 패키지 │
│ - 템플릿 + 기본값 + 메타데이터 │
│ │
│ Release │
│ - Chart의 설치된 인스턴스 │
│ - 같은 Chart로 여러 Release 가능 │
│ │
│ Repository │
│ - Chart 저장소 │
└─────────────────────────────────────────────┘
|
주요 개념:
- Chart: 애플리케이션을 정의하는 패키지
- Release: Chart를 클러스터에 설치한 인스턴스
- Repository: Chart를 저장하고 공유하는 저장소
Helm 설치
1
2
3
4
5
6
7
8
| # macOS
brew install helm
# Linux
curl https://raw.githubusercontent.com/helm/helm/main/scripts/get-helm-3 | bash
# 버전 확인
helm version
|
기본 명령어
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
38
39
40
| # Repository 추가
helm repo add bitnami https://charts.bitnami.com/bitnami
helm repo add stable https://charts.helm.sh/stable
helm repo update
# Chart 검색
helm search repo nginx
helm search hub nginx # Artifact Hub 검색
# Chart 정보 확인
helm show chart bitnami/nginx
helm show values bitnami/nginx # 설정 가능한 값
# Chart 설치
helm install my-nginx bitnami/nginx
helm install my-nginx bitnami/nginx --namespace web --create-namespace
# 커스텀 값으로 설치
helm install my-nginx bitnami/nginx -f values.yaml
helm install my-nginx bitnami/nginx --set replicaCount=3
# Release 목록
helm list
helm list -A # 모든 namespace
# Release 상태
helm status my-nginx
# Release 업그레이드
helm upgrade my-nginx bitnami/nginx --set replicaCount=5
helm upgrade my-nginx bitnami/nginx -f new-values.yaml
# Release 롤백
helm rollback my-nginx 1 # 리비전 번호
# Release 삭제
helm uninstall my-nginx
# Release 히스토리
helm history my-nginx
|
Chart 구조
1
2
3
4
5
6
7
8
9
10
11
| mychart/
├── Chart.yaml # Chart 메타데이터
├── values.yaml # 기본 설정값
├── charts/ # 의존성 Chart
├── templates/ # 템플릿 파일
│ ├── deployment.yaml
│ ├── service.yaml
│ ├── ingress.yaml
│ ├── _helpers.tpl # 템플릿 헬퍼
│ └── NOTES.txt # 설치 후 메시지
└── .helmignore # 패키징 제외 파일
|
Chart.yaml
1
2
3
4
5
6
7
8
9
10
| apiVersion: v2
name: mychart
description: My application chart
type: application
version: 0.1.0 # Chart 버전
appVersion: "1.16.0" # 애플리케이션 버전
dependencies:
- name: postgresql
version: "12.x.x"
repository: https://charts.bitnami.com/bitnami
|
values.yaml
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
| # 기본 설정값
replicaCount: 1
image:
repository: nginx
tag: "1.24"
pullPolicy: IfNotPresent
service:
type: ClusterIP
port: 80
resources:
limits:
cpu: 100m
memory: 128Mi
requests:
cpu: 50m
memory: 64Mi
nodeSelector: {}
tolerations: []
affinity: {}
|
템플릿 작성
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
| # templates/deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
name:
labels:
spec:
replicas:
selector:
matchLabels:
template:
metadata:
labels:
spec:
containers:
- name:
image: ":"
imagePullPolicy:
ports:
- containerPort: 80
resources:
|
템플릿 함수
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
| # 문자열 함수
# 대문자
# 소문자
# 첫글자 대문자
# 따옴표 추가
# 기본값
# 조건문
apiVersion: networking.k8s.io/v1
kind: Ingress
...
# 반복문
- host:
# 변수# YAML 변환
|
Chart 개발
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
| # 새 Chart 생성
helm create mychart
# 템플릿 렌더링 (디버깅)
helm template my-release ./mychart
helm template my-release ./mychart -f custom-values.yaml
# 문법 검사
helm lint ./mychart
# 설치 전 미리보기 (dry-run)
helm install my-release ./mychart --dry-run --debug
# Chart 패키징
helm package ./mychart
# 의존성 관리
helm dependency update ./mychart
|
Kustomize
Kustomize 개요
Kustomize는 템플릿 없이 YAML을 커스터마이징한다.
1
| Base YAML + Overlay = 최종 YAML
|
특징:
- kubectl에 내장 (
kubectl apply -k) - 원본 YAML 수정 없이 오버레이
- 환경별 설정 관리에 적합
기본 구조
1
2
3
4
5
6
7
8
9
10
11
| ├── base/ # 기본 리소스
│ ├── kustomization.yaml
│ ├── deployment.yaml
│ └── service.yaml
└── overlays/ # 환경별 오버레이
├── development/
│ ├── kustomization.yaml
│ └── replica-patch.yaml
└── production/
├── kustomization.yaml
└── replica-patch.yaml
|
base/kustomization.yaml
1
2
3
4
5
6
| apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization
resources:
- deployment.yaml
- service.yaml
|
base/deployment.yaml
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
| apiVersion: apps/v1
kind: Deployment
metadata:
name: myapp
spec:
replicas: 1
selector:
matchLabels:
app: myapp
template:
metadata:
labels:
app: myapp
spec:
containers:
- name: myapp
image: myapp:latest
ports:
- containerPort: 8080
|
overlays/production/kustomization.yaml
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
| apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization
resources:
- ../../base
namespace: production
namePrefix: prod-
nameSuffix: -v1
commonLabels:
env: production
commonAnnotations:
managed-by: kustomize
replicas:
- name: myapp
count: 5
images:
- name: myapp
newTag: "1.0.0"
patches:
- path: replica-patch.yaml
|
패치 방식
Strategic Merge Patch:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
| # overlays/production/replica-patch.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
name: myapp
spec:
replicas: 5
template:
spec:
containers:
- name: myapp
resources:
limits:
cpu: "500m"
memory: "256Mi"
|
JSON Patch:
1
2
3
4
5
6
7
8
9
| # kustomization.yaml
patches:
- target:
kind: Deployment
name: myapp
patch: |-
- op: replace
path: /spec/replicas
value: 5
|
Kustomize 사용
1
2
3
4
5
6
7
8
9
10
| # 빌드 (YAML 출력)
kustomize build overlays/production/
kubectl kustomize overlays/production/
# 적용
kustomize build overlays/production/ | kubectl apply -f -
kubectl apply -k overlays/production/
# 삭제
kubectl delete -k overlays/production/
|
ConfigMap/Secret 생성
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
| # kustomization.yaml
configMapGenerator:
- name: app-config
literals:
- LOG_LEVEL=info
- DB_HOST=localhost
- name: app-config-file
files:
- config.json
secretGenerator:
- name: db-secret
literals:
- username=admin
- password=secret123
generatorOptions:
disableNameSuffixHash: true # 해시 접미사 비활성화
|
이미지 변경
1
2
3
4
5
6
7
| # kustomization.yaml
images:
- name: myapp
newName: registry.example.com/myapp
newTag: "2.0.0"
- name: nginx
digest: sha256:abc123... # digest로 지정
|
Helm vs Kustomize
| 특성 | Helm | Kustomize |
|---|
| 방식 | 템플릿 | 오버레이 |
| 복잡도 | 높음 | 낮음 |
| 학습 곡선 | 가파름 | 완만함 |
| 패키지 배포 | 적합 | 부적합 |
| 환경별 설정 | 가능 | 매우 적합 |
| 커뮤니티 Chart | 풍부 | 해당없음 |
| kubectl 통합 | 별도 설치 | 내장 |
사용 시나리오:
- Helm: 복잡한 애플리케이션, 커뮤니티 Chart 사용, 릴리스 관리 필요
- Kustomize: 환경별 설정 관리, 간단한 커스터마이징, GitOps
함께 사용하기
1
2
3
4
| # Helm Chart를 Kustomize로 커스터마이징
helm template my-release bitnami/nginx > base/nginx.yaml
# kustomization.yaml에서 patches 적용
|
기술 면접 대비
자주 묻는 질문
Q: Helm Chart와 Release의 차이는?
A: Chart는 애플리케이션을 정의하는 패키지(템플릿과 기본값의 묶음)이다. Release는 Chart를 클러스터에 설치한 인스턴스이다. 같은 Chart로 여러 Release를 만들 수 있으며, 각 Release는 독립적으로 업그레이드하고 롤백할 수 있다.
Q: Helm 3와 Helm 2의 차이점은?
A: Helm 3에서 Tiller(클러스터 내 서버 컴포넌트)가 제거되었다. 이로써 RBAC 설정이 간소화되고 보안이 향상되었다. Release 정보는 Secret으로 저장되며, 클라이언트가 직접 API Server와 통신한다.
Q: Kustomize의 장점은?
A: 원본 YAML을 수정하지 않고 오버레이로 커스터마이징한다. 템플릿 언어를 배울 필요 없이 순수 YAML로 작업한다. kubectl에 내장되어 별도 설치가 필요 없다. 환경별 설정 관리에 매우 적합하다.
Q: Helm과 Kustomize를 함께 사용하는 이유는?
A: Helm은 복잡한 애플리케이션 패키징과 커뮤니티 Chart 활용에 좋고, Kustomize는 환경별 세밀한 커스터마이징에 좋다. Helm Chart를 렌더링한 후 Kustomize로 환경별 패치를 적용하는 방식으로 두 도구의 장점을 결합할 수 있다.
CKA 시험 대비 필수 명령어
CKA 시험에서는 주로 Kustomize가 출제된다.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
| # Kustomize 빌드
kubectl kustomize <directory>
# Kustomize 적용
kubectl apply -k <directory>
# Kustomize 삭제
kubectl delete -k <directory>
# Helm (기본 명령)
helm install <release> <chart>
helm upgrade <release> <chart>
helm list
helm uninstall <release>
|
다음 단계