만료/변경된 imagePullSecrets을 관리하기 위해 만든 imagepullsecrets-manager를 소개한다.
https://github.com/GeunjeLEE/private-registry-secret-manager
현재 팀의 서비스는 오픈소스로 되어있기 때문에 github는 물론 docker hub도 공개되어있다.
하지만 최근 private(코드를 공개하지 않는) 프로젝트의 CI/CD를 구축할 일이 생기면서
상당히 귀찮은 상황을 마주하게 되었다.
github는 물론이고 docker image역시 private repository을 사용한다는 것이 그것인데,
kubernetes에서 private image를 받아오기 위해서는 credential이 필요하다는 것은 누구나 아는 사실...
나 역시도 이러한 사실을 알고 착실히 credential을 생성하고, (k8s의)secret으로 만들어 일단은 배포에 성공했더랬다...
처음 CI/CD를 구축하면서 배포를 위해 imager repository의 credential을 적용할 수 있는 방법을 찾아봤는데 kubernetes 공식 문서에는 아래와 같은 private image를 위해 credential을 제공하는 방법을 제시하고 있었다.
1번의 경우 worker node에 뛰어들어서 일일히 설정 잡는게 불편하다고 느꼈고,
2번의 경우 사실 저걸 왜 언급한건지 이해하지 못했다, 어차피 registry에서 받아와야하는데...
3번의 경우 가장 많이 눈에 띄는 방법이었다. (blog에서 많이 찾아볼 수 있었다.)
4번의 경우 필요하면 너가 구현해
라고 말하는 것 같았다.
때문에 3번의 방법으로 일단 최초 배포를 해둔 상태였다.
최조 배포 후, 조금 불안불안하긴 했으나 아니나 다를까.
얼마 뒤 pod가 image를 받아오지 못해 배포에 실패하는 현상을 마주하고 말았다.
Failed to pull image "registry.example.com/private-image:latest": rpc error: code = Unknown desc = Error response from daemon: pull access denied for registry.example.com/private-image:latest, repository does not exist or may require 'docker login': denied: requested access to the resource is denied
살펴보니 ECR의 credential, 즉 aws get-login-password
로 발급한 authorization token은 12시간의 유효기간을 가지고 있었고역시나 그것이 문제였다.(아...앙대... 배포 자동화....ㅠㅠ)
private image를 위해 repository에 접근하는 것이 아닌, 접근을 위한 credential이 문제가 되는 것 이었다.
이러한 credential을 자동으로 관리하기 위해 구글링을 해보았더니 이미 너드형들이 여러 솔루션을 만들어두고 블로그에 자랑하고 있었다. (admission controller로 구현해놓은 형님도 봤다..!)
몇 가지를 살펴보면서 느낀건 대단하긴 한데, 내가 도저히 따라갈 수 없었다.(혹은 너무 설정하기 복잡했다.)
그래서 나는 내 방식으로 만들고 더 나아가 나같이 코만 파고있는 사람들도 쉽게 사용할 수 있도록 만들고 싶었다.
그래서 만든 것이 imagePullSecrets-manager
인데 kubernetes cronjob으로 움직이는 간단한 python script이다.
자신이 생성/관리하고 싶은 repository login 정보를 설정해두기만 하면 imagePullSecrets-manager
가 나타나서 대신 생성하고, 관리해준다.
ECR
과 DOCKERHUB
에 대한 유형을 지원한다.ECR
get-login-password
로 토큰을 발급해 imagePullSecrets을 업데이트한다.DOCKERHUB
helm chart를 만들어두었기 때문에 쉽게 배포할 수 있다.
아래의 툴이 필요하다.
$ git clone https://github.com/GeunjeLEE/imagepullsecrets-manager.git
$ cd imagepullsecrets-manager
$ vim helm/values.yaml
---
name: imagepullsecrets-manager
namespace: default
image:
name: nigasa12/imagepullsecrets-manager
version: <image-version> # 2020.07.06기준 1.0.0
imagePullPolicy: IfNotPresent
job_schedule: "* * * * *" # cron schedule / default every minute
successfulJobsHistoryLimit: 10
config:
secrets: # 생성할 imagepullsecrets의 credential
- name: ecr-example
kubernetes_namespace: default
type: ECR
credential:
aws_access_key_id: foobargem
aws_secret_access_key: foobargem
aws_ecr_repository_region: ap-northeast-2
- name: docker-example
kubernetes_namespace: default
type: DOCKER
credential:
docker_registry: docker.io
docker_user: foobargem
docker_password: password
docker_email: foobargem@example.com
$ helm install imagepullsecrets-manager ./helm
$ helm upgrade imagepullsecrets-manager ./helm
$ helm uninstall imagepullsecrets-manager
현재 팀의 개발환경에도 imagepullsecrets-manager
를 배포하고 운영해보고 있다.
당연히 현재는 pod가 image를 받아오지 못해 배포에 실패하는 현상은 발생하지 않고 있다.
이러한 것은 imagepullsecrets-manager
가 항상 imagepullsecrets
를 노려보며 유효기간이 지났는지 체크해주고 있기 때문이다.
이것으로 내가 수시로 imagepullsecrets
가 만료되지 않았는지 확인하는 일은 하지 않아도 된다.(어렵사리 이어붙힌 CI/CD 자동화...)
현재 팀이 너무나도 바쁜 상황이라 code review도 이루어지지 않은 허접한 코드이지만
앞으로 상황이 나아지면 팀 시니어 개발자들에게도 소개하고 code review도 진행해서 상용환경에도 적용해보고 싶은 마음이다.