Kubernetes/Kubernetes_Service

[Kubernetes] ArgoCD를 사용한 EKS 자동배포(3) - ArgoCD ImageUpdater

달콤한달팽이 2024. 12. 11. 16:42
반응형

안녕하세요, 달콤한달팽이입니다.🐌🙂

 

이번 시간에는 마지막으로 ArgoCD ImageUpdater를 설치하고,

이를 통해 자동 이미지 배포 환경을 구현해보도록  하겠습니다.


ArgoCD ImageUpdater란?

ArgoCD ImageUpdater란, ArgoCD에서 관리하는 Kubernetes 환경 컨테이너 이미지 자동 업데이트 도구입니다.

즉, ArgoCD Application에 어노테이션 값을 기준으로 이미지 버전을 추적하고 업데이트를 도와주는 도구입니다.


그럼 이제 지난 번에 이어 ArgoCD ImageUpdatger를 설치하고 적용해보는 과정을 수행해보겠습니다.
 
 

5) Image Updater 적용

우선, ArgoCD ImageUpdater를 설치해주세요.

 

정상적으로 설치가 되었다면, argocd-image-updater라는 Deployment가 생성되었을 것입니다.

$ kubectl apply -n argocd -f https://raw.githubusercontent.com/argoproj-labs/argocd-image-updater/stable/manifests/install.yaml

$ kubectl get all -n argocd | grep image-updater

 

이제 ArgoCD API 사용을 위한 API용 계정을 생성하고 확인해주세요.

$ argocd login {ArgoCD 주소}
$ kubectl edit configmap argocd-cm -n argocd

--- configmap 추가 ---
data:
  accounts.image-updater: apiKey

$ argocd account list

 

다음은 앞서 생성한 image-updater 유저에 애플리케이션을 받아오고, 업데이트하기 위한 권한을 부여해주도록 하겠습니다.

$ kubectl edit configmap argocd-rbac-cm -n argocd

--- configmap 추가 ---
data:
  policy.csv: |
    p, role:image-updater, applications, get, */*, allow
    p, role:image-updater, applications, update, */*, allow
    g, image-updater, role:image-updater
  policy.default: role.readonly

 

ArgoCD를 통해 ECR 이미지를 다운로드 가능하도록 ECR 레포지토리를 등록해주세요.

$ kubectl edit configmap argocd-image-updater-config -n argocd

--- configmap 추가 ---
data:
  applications_api: argocd
  argocd.grpc_web: "true"
  argocd.insecure: "false"
  argocd.plaintext: "false"
  argocd.server_addr: {ArgoCD 주소}
  log.level: debug
  registries.conf: |
    registries:
      - name: AWS ECR HUB
        api_url: https://{계정ID}.dkr.ecr.{리전}.amazonaws.com
        prefix: {계정ID}.dkr.ecr.{리전}.amazonaws.com
        ping: yes
        credentials: ext:/tmp/aws/ecr.sh

 

프라이빗 레포지토리(ECR)에서 이미지를 가져오기 위해선 그에 대한 secret을 생성하고, 토큰을 생성해야합니다.

 

우선 아래와 같이 secret을 먼저 생성해주도록 합니다.

$ kubectl create secret docker-registry aws-ecr-creds \
--docker-server={ECR URI} \
--docker-username=AWS \
--docker-password=$(aws ecr get-login-password) \
-n argocd

 

이후 Image Updater 계정에 대한 토큰을 발행해주세요.

(** 주의: 토큰값은 한 번 출력된 이후 다시 출력되지 않으니 잘 복사해주세요!)

 

이제 위 토큰값을 사용하여 secret을 생성해주세요.

$ kubectl create secret generic argocd-image-updater-secret \
  --from-literal argocd.token={토큰값} --dry-run -o yaml |
  kubectl -n argocd apply -f -

 

image-updater 컨테이너는 ECR의 이미지를 주기적으로 가져가야하므로 토큰값이 동적으로 부여되도록 컨테이너 내부에 쉘 스크립트를 작성하도록 하겠습니다.

(만약 부여된 토큰값을 정적으로 넣게될 경우, 토큰값이 만료될 때 마다 다시 토큰값을 만들어서 넣어줘야하는 번거로움이 있습니다!)

$ kubectl -n argocd exec --stdin --tty pod/{argocd-image-updater Pod} -- /bin/sh

--- 컨테이너 내부 ---
$ cd tmp
$ mkdir aws
$ cd aws
$ vi ecr.sh

--- ecr.sh ---
#!/bin/sh
aws ecr --region ap-northeast-2 get-authorization-token --output text --query 'authorizationData[].authorizationToken' | base64 -d

 

tmp 파일경로에서 위 작업을 수행하는 이유는 모든 파일 중 tmp 파일만이 쓰기 가능한 권한이 있기 때문입니다.

이제 컨테이너 내부에서 ecr.sh 파일이 정상적으로 동작하는지 테스트를 수행해주세요.

(아래처럼 WARN, INFO만 나오면 정상입니다!)

$ chmod +x /tmp/aws/ecr.sh
$ argocd-image-updater test \
 {ECR 레포지토리 URI} \
 --registries-conf-path /app/config/registries.conf

 

혹시 위 과정에서 아래와 같은 에러가 발생하며 동작하지 않는다면 아래의 접힌글을 참고해주세요!

더보기

해당 이슈는 /app 경로 내에 쓰기 권한이 없기 때문에 aws configure를 통한 인증이 불가하여 발생하는 이슈입니다.

 

1) Secret 추가

우선, 아래 명령어를 수행해 image-updater secret에 접근해주세요.

$ kubectl edit secret argocd-image-updater-secret -n argocd

 

이후 아래 문구를 추가해주세요.

(아래의 키(key)값은 aws credential 정보를 공유하기 위한 경로를 지정하는 것이고,

값(value)은 /tmp/.aws/credentials를 base64로 인코딩한 값입니다.)

AWS_SHARED_CREDENTIALS_FILE: L3RtcC8uYXdzL2NyZWRlbnRpYWxz

 

2) Deployment 환경변수 추가

다음에 secret에 추가한 값을 deployment의 환경변수로 추가하여, Deployment를 통해 생성된 Pod이 이를 기본적으로 사용할 수 있도록 지정해주세요.

$ kubectl edit deployment argocd-image-updater -n argocd

 

Deployment 내부에 secretKeyRef의 마지막부분에 아래와 같은 값을 추가해주세요.

        - name: AWS_SHARED_CREDENTIALS_FILE
          valueFrom:
            secretKeyRef:
              key: AWS_SHARED_CREDENTIALS_FILE
              name: argocd-image-updater-secret

3) Deployment 재시작

이제 환경변수가 적용될 수 있도록 Deployment를 재시작해주세요.
$ kubectl rollout restart deployment argocd-image-updater -n argocd

 

4) 환경변수 확인

이제 마지막으로 컨테이너 내부에 다시 접속하여 환경변수가 제대로 들어갔는지 확인해주세요.

$ kubectl -n argocd exec --stdin --tty pod/{ArgoCD ImageUpdater Pod ID} -- /bin/sh

--- 컨테이너 내부 ---
$ env | grep AWS
$ cd tmp
$ mkdir .aws
$ aws configure # AccessKey, Secret Access Key, Region 등록
$ aws configure # 정상 등록 확인

 

이후 다시 이전에 수행했던 ecr.sh 파일을 만들고 권한 변경을 수행하면 끝입니다! 

 

이제 ArgoCD 애플리케이션의 어노테이션을 설정해주도록 합시다.

 1) image-list : 업데이트할 이미지의 이름과 태그 설정

 2) image-tag-sort-mode : 이미지 태그를 정렬하는 방식 설정

 2) pull-secret : 프라이빗 레지스트리에서 이미지를 가져올 때 사용하는 인증 정보 설정

 3) update-strategy : 이미지 업데이트 시 어떤 전략을 사용할지 설정(latest / semver / specific)

 4) write-back-method : 업데이트 된 이미지 버전을 Git 레포지토리에 반영하는 방법 설정(git / helm / kustomize)

argocd-image-updater.argoproj.io/image-list -> org/app={REPOSITORY URI}
argocd-image-updater.argoproj.io/image-tag-sort-mode -> time
argocd-image-updater.argoproj.io/org_app.pull-secret -> ext:/tmp/aws/ecr.sh
argocd-image-updater.argoproj.io/update-strategy -> latest
argocd-image-updater.argoproj.io/write-back-method -> git

 

이제 모든 구성이 완료되었습니다!

 

마지막으로 CI/CD 환경이 원하는대로 구성되었는지 확인해보도록 합시다.

 

6) 자동배포 확인

현재 

애플리케이션의 Pod의 상세 정보를 통해 현재 어떤 이미지 버전이 적용되어있는지 확인해주세요.

 

코드 변경 전에는 2b7665e라는 태그값을 가진 이미지로 Pod가 배포되어 있는걸 확인할 수 있습니다.

 

이제 BitBucket 내부의 코드를 수정한 후 다시 배포하여 CodePipeline이 동작하는지, ECR 이미지가 생성되었는지 확인해주세요!

(여기서는 a264f72라는 태그를 가진 이미지가 새로 생겼네요!)

 

이제 조금 기다린 이후 ArgoCD Refresh를 눌러주어 새로운 Pod가 배포되었는지 확인해주세요.

(조금 기다리는 이유는 ArgoCD ImageUpdater가 ECR의 변경사항을 감지하기 위한 디폴트 시간이 3분이기 때문입니다!)

 

위와 같이 신규 이미지로 변경이 되었다면 이번 구축은 성공입니다!

 

이제 BitBucket의 소스 코드를 수정해도, 신규 이미지가 등록되어도 ArgoCD가 이를 자동으로 감지하여 배포해줄거예요!


지금까지 ArgoCD를 활용하여 EKS CI/CD 환경 구축하는 방법을 알아보았습니다.

 

이를 구축하기 위해 다른 여러 블로그를 참고했지만

권한 오류, 어노테이션 오류 등 너무 많은 시행착오가 있어 시간이 너무 오래걸렸네요!

 

이 글을 읽으시는 분들은 막힘없이 구축하셨으면 좋겠습니다 :) 

 

긴 글 읽어주셔서 감사합니다!

반응형