헬름(Helm)

본 문서는 쿠버네티스 패키지 매니저인 헬름(Helm)에 대한 정보와 헬름 차트(Chart) 작성법에 대한 가이드라인을 제공한다.

헬름(Helm)이란

Helm은 쿠버네티스 애플리케이션을 패키지 형태로 손쉽게 관리할 수 있도록 도와주는 도구다. 디플로이먼트(Deployment), 스테이트풀셋(Statefulset)과 같은 컴퓨팅 자원, 서비스(Service)나 인그레스(Ingress)와 같은 디스커버리/로드밸런싱 자원에 대한 정의를 템플릿 기반의 YAML로 작성하여 배포할 수 있다. 템플릿 엔진을 활용함으로써 여러 배포환경에 대한 반복적인 API 오브젝트 정의를 하지 않고 별도의 YAML 파일에 배포환경별로 달라지는 내용만 따로 명시하여 덮어쓸 수 있다. 릴리즈에 대한 버전 관리 또한 지원하여 문제가 발생할 시 CLI를 이용해 간단히 롤백 할 수 있다.

다만 버즈빌에서는 Helm의 템플릿 엔진만을 이용하고, 실제 릴리즈 관리는 Spinnaker라는 CD(Continuous Delivery) 플랫폼에서 이뤄진다. Spinnaker는 Helm을 이용해 템플릿을 렌더링하고 직접 쿠버네티스 클러스터에 반영하게 된다.

헬름 구성 요소

  • Client: Helm CLI.
  • Tiller: 쿠버네티스 클러스터쪽에 설치되는 컴포넌트. CLI와 통신하여 클러스터에 실제로 반영하는 역할을 담당.

참고: 향후 릴리즈될 Helm 3 버전에서는 서버 컴포넌트인 Tiller에 권한이 과하게 부여되는 문제 때문에 클라이언트 전용 방식으로 바뀔 예정이다.

헬름 차트(Chart)

Helm 차트라는 패키징 포맷을 사용한다. 차트는 쿠버네티스 리소스의 묶음을 템플릿 형태로 관리하며, 하나의 차트가 여러 개의 하위 차트(subchart)를 포함하는 방식으로 복잡한 워크로드를 정의하는 것도 가능하다. 필요한 경우 쿠버네티스 기본 리소스 뿐 아니라 Istio와 같은 서비스 메쉬에서 필요한 VirtualService, Gateway, 또는 Cert Manager에서 관리할 Certificate 리소스와 같은 CRD(Custom Resource Definition)도 포함할 수 있다.

버즈빌 내부 서비스에 대한 차트 정의는 charts에서 모노 리포 형태로 관리하고 있다. 이 모노 리포는 Helm 공식 차트 리포지토리와 비슷한 방식으로 구성된다. 차트 변경사항은 master 브랜치에 머지되면 CI를 통해 사내 차트 레지스트리에 업로드된다. 사내 차트 리포지토리의 구성 및 사용법은 README를 참조한다.

차트 만들기

버즈빌 내부 서비스에 대한 차트는 개별 프로젝트가 아닌 차트 모노 리포에서 관리한다. 모노 리포를 사용하면 차트에 대한 lint, test, 릴리즈 등에 대한 CI를 프로젝트마다 별도로 세팅하지 않고 한 곳에서 처리할 수 있는 장점이 있다.

차트 작성은 버즈빌 헬름 차트 모노리포에서 CLI로 시작한다.

$ helm create PROJECT_NAME
> Creating PROJECT_NAME

작성된 차트는 일반적으로 아래와 같은 구조로 이루어진다.

buzzscreen
├── Chart.yaml
├── templates
│   ├── _helpers.tpl
│   ├── configmap.yaml
│   ├── deployment.yaml
│   ├── fluentd-configmap.yaml
│   ├── fluentd-file-configmap.yaml
│   ├── hpa.yaml
│   ├── pdb.yaml
│   ├── secret.yaml
│   ├── service.yaml
│   └── virtualservice.yaml
└── values.yaml
  • 차트 이름을 프로젝트 이름과 가능한 한 동일하게 생성하고, Chart.yaml에 적절한 description을 입력한다.
  • helm create으로 기본 생성되는 파일 중 NOTES.txttests 디렉토리는 사용하지 않으므로 제거한다.
  • helper를 사용하여 여러 템플릿에 반복적으로 사용되는 labels, matchLabels 같은 표현의 반복을 줄인다(authsvc example 참고).
  • 배포하려는 서비스가 게이트웨이를 통해 직접 접근되는 경우 VirtualService를 정의한다. Istio의 Gateway를 사용하지 못하는 일부 케이스의 경우 Ingress를 정의한다. 클러스터 내부에서만 사용되는 경우 Service만 정의한다.
  • 가능하면 각 차트 내에 README 파일을 추가하여 value에 대한 설명, 배포 시 유의사항 등에 대한 설명을 추가한다. 공식 헬름 stable 차트 리포의 차트를 참고한다(i.e. mysql example).
  • 차트를 작성할 때 VS Code의 쿠버네티스 공식 익스텐션을 사용하면 신텍스 하이라이팅, 린트, 자동완성, 템플릿 출력 테스트 등을 해볼 수 있다.
  • 운영 중인 서비스의 안정성을 위해 PDB(Pod Disruption Budget), HPA(Horizontal Pod Autoscaler)도 차트에 함께 정의한다.

이외에도 공식 리포지토리의 The Chart Best Practices Guide를 참고하는 것을 권장한다.

배포 환경별 헬름(Helm) value 파일 작성

각 차트는 릴리즈 시에 value를 바인딩함으로써 각 차트마다 values.yaml에 기본값으로 정의된 value들을 덮어쓸 수 있다. 헬름 CLI를 이용하는 경우 덮어쓸 value가 정의된 YAML 파일을 지정하거나, --set 플래그를 이용해 개별적인 값들을 덮어쓸 수 있다. 버즈빌에서는 헬름 차트 배포를 스피네커(Spinnaker)를 이용해서 진행하는데, 이때는 덮어쓸 values를 배포환경별로 별도의 모노리포를 통해 관리하고, 배포 시점에 스피네커가 해당하는 환경의 설정 파일을 읽어와 헬름 템플릿을 렌더링한다. 이를 통해 앱과 설정을 분리하여 배포하는 방식이 가능하다.

커스텀 메트릭으로 HPA 만들기(Autoscaling v2)

TBD