LabHub
배우기 러닝패스 코스

CNPE — クラウドネイティブプラットフォームエンジニア

ゲートをどこに置くか

LabHub 에서 이어서 보기

한국어 원문으로 표시합니다.

한 줄 요약

배포 파이프라인의 게이트는 소스가 아니라 렌더 결과에 걸어야 합니다. 클러스터에 들어가는 것은 파일이 아니라 렌더된 매니페스트이고, 게이트가 보지 않은 것은 막을 수 없기 때문입니다.

概念マップ: 소스가 아니라 렌더 결과・자기가 막으려는 대상을 보고 있지 않아서・검사 결과를 종료 코드로 옮기는 것・막아야 할 것을 실제로 넣어 보고 빨간불이 켜지는지

왜 렌더 결과인가

kustomize 오버레이 세 개짜리 저장소에서 흔히 이런 게이트를 봅니다.

grep -r "image:.*:latest" .   # latest 태그 금지

이 검사는 base 를 보고 통과합니다. 그런데 실제로 배포되는 것은 오버레이가 이미지를 덮은 결과이고, 그 결과에는 latest 가 들어 있을 수 있습니다. 반대도 성립합니다. base 에 latest 가 있어도 오버레이가 다이제스트로 덮으면 배포되는 것은 안전한데, 게이트는 빨간불을 켭니다.

두 경우 모두 게이트가 자기가 막으려는 대상을 보고 있지 않아서 생깁니다. 그래서 순서는 하나뿐입니다.

kustomize build overlays/prod   →   렌더 결과
        ↓
스키마 검증 · 정책 검사          →   이 결과를 검사한다
        ↓
0 이 아닌 종료 코드면 배포 중단

어떻게 동작하나

게이트는 종료 코드로 말해야 합니다

정책 도구를 돌려 놓고 결과를 화면에만 뿌리고 끝내는 파이프라인이 정말 많습니다. 로그에는 빨간 글씨가 있고 파이프라인은 초록불입니다. 게이트의 본체는 검사가 아니라 검사 결과를 종료 코드로 옮기는 것입니다.

if ! kyverno apply policy/require-pinned.yaml --resource "$RENDER"; then
  echo "정책 위반으로 배포를 막습니다"; exit 3
fi

그리고 게이트를 만들었으면 막아야 할 것을 실제로 넣어 보고 빨간불이 켜지는지 확인해야 합니다. 통과하는 것만 확인한 게이트는 몇 달 동안 아무것도 지키지 않은 채로 초록불을 냅니다.

태그가 아니라 다이제스트

checkout:1.4.0 은 이름이고 checkout@sha256:... 은 내용입니다. 태그는 다시 밀 수 있어서, 어제 검증한 것과 오늘 배포되는 것이 다를 수 있습니다. 다이제스트로 고정하면 "게이트를 통과한 그것" 과 "클러스터에 들어간 그것" 이 같다는 것을 말할 수 있습니다. 감사 추적이 성립하는 최소 조건입니다.

진행형 배포는 멈춤이 본체입니다

카나리를 setWeight: 10setWeight: 100 으로 적어 두면 그건 카나리가 아니라 조금 느린 전면 배포입니다. 가중치 사이에 pause 가 있어야 사람이나 분석이 판단할 자리가 생깁니다. 그리고 카나리만 따로 볼 수 있어야 판단할 근거가 생기므로, canaryServicestableService 를 나눠 둡니다.

블루/그린은 새 버전을 미리보기 통로로 확인한 뒤 트래픽을 전환하는 선택지입니다. autoPromotionEnabled: false 는 자동 승격을 막습니다. 하지만 미리보기 버전도 시작 작업이나 백그라운드 작업으로 데이터를 쓸 수 있습니다. 원장처럼 단일 writer가 필요한 서비스는 쓰기 제어·스키마 호환·복구 절차를 별도로 검증해야 합니다. 블루/그린이 동시 쓰기를 막는다는 뜻은 아닙니다.

현장에서 만나는 모습

한 조직에서 카나리 분석이 계속 통과했는데 장애가 났습니다. 원인은 분석 템플릿 이름을 오타 낸 것이었습니다. Rollout 은 없는 템플릿을 참조하고 있었고, 그 사실은 승격 직전에야 드러났습니다. 그래서 "참조한 템플릿이 실제로 있는가" 는 배포 전에 확인할 항목입니다.

또 하나 자주 보는 것은 Argo CD Application 의 목적지 네임스페이스와 매니페스트가 렌더되는 네임스페이스가 어긋나 있는 경우입니다. 동기화는 성공하고 초록불이 뜨는데 아무 데도 반영되지 않습니다.

초록불이 거짓말하는 자리

앞에서 본 두 사례(없는 분석 템플릿, 어긋난 목적지 네임스페이스)에는 공통점이 있다. 동기화는 성공했는데 아무 일도 일어나지 않았다는 것이다. GitOps 에서 초록불이 뜻하는 것은 "git 과 클러스터가 같다" 이지 "서비스가 정상이다" 가 아니다. 이 둘을 헷갈리면 화면만 보고 안심하게 된다.

초록불이 거짓말하는 자리는 몇 군데로 정해져 있다.

아무것도 안 만들어졌는데 같다고 한다. 매니페스트가 렌더된 결과가 비어 있으면 "관리할 것이 없으니 차이도 없다" 가 되어 동기화가 성공한다. 오버레이 경로를 잘못 적었거나 선택자가 아무것도 안 고르는 경우다. 관리 대상 개수를 함께 보는 것이 이것을 잡는 가장 값싼 방법이다.

적용됐지만 컨트롤러가 거부했다. 오브젝트는 만들어졌으므로 git 과 클러스터는 같지만, 그 오브젝트를 읽는 컨트롤러가 값을 거부하고 상태에만 오류를 적어 둔다. Rollout·Certificate·ExternalSecret 처럼 다른 컨트롤러가 처리하는 것이 여기 해당한다. 그래서 건강 판정을 오브젝트 존재가 아니라 상태 필드로 하는 설정이 필요하다.

무시 규칙이 진짜 차이까지 덮는다. 자동 확장이 복제 수를 바꾸는 것을 차이로 보지 않으려고 무시 규칙을 넣는데, 그 범위가 넓으면 사람이 손으로 바꾼 것까지 함께 덮인다. 그때부터 그 필드는 GitOps 밖에 있다.

그래서 초록불 옆에 다른 신호를 하나 더 둔다. 마지막으로 동기화한 커밋이 무엇인지, 그리고 지금 도는 이미지의 태그가 무엇인지다. 둘이 기대와 다르면 초록불과 무관하게 무언가 잘못된 것이고, 이 대조는 몇 초면 끝난다.

다음 실습에서 할 것

base 와 운영 오버레이를 만들고, 렌더 결과에 정책 게이트를 걸고, 그 게이트가 위반을 실제로 막는지 확인한 뒤, 카나리와 블루/그린을 각각 어떤 서비스에 붙일지 정합니다.