본문 바로가기
Argo-CD

Github Action, Kubernetes 설정파일 관리 with Argo-CD

by 준형코딩 2023. 9. 20.

 
 

 

 

 

쿠버네티스에 스프링부트 프로젝트를 배포하고 Github Action과 Argo-CD를 통해서 CI/CD도 거의 완료 단계에 들어가게 되었다. 그러나 로컬에 들어있는 application.yml 파일들이나 FCM을 동작하게 해주는 FCM 인증서 JSON 파일은 깃 레포지토리에서 관리를 하고 있지 않았기 때문에 CI/CD 파이프라인을 타게 되면 설정이 빠진 스프링 프로젝트가 배포되는 문제가 있었다. 그래서 어떻게 하면 application.yml에 들어있는 DB 중요정보나 FCM 인증서를 레포지토리에서 관리하지 않고도 CI/CD 파이프라인을 통해서 문제없이 설정 정보까지 배포를 할 수 있을까 고민을 하게 되었다. 

먼저 application.yml에 들어있는 중요정보들은 쉽게 해결할 수 있었다. 쿠버네티스에 존재하는 configmap 설정이나 secret을 통해서 변수를 만들어서 deployment에 할당을 해주거나 아니면 github secret을 생성한 뒤 application-prod.yaml을 깃 레포지토리에 만들어준 뒤 중요 정보들은 ${{secrets.DB_PASSWORD}} 이런 식으로 가져오게 되었다.


그러나 여기서 문제는 FCM 인증서였다. FCM 인증서 같은 경우는 json 파일로 이루어져 있었기 때문에 기존 yaml 파일처럼 github secret이나 configmap을 설정하여 간단하게 레포지토리에 빈 json을 만들어준 뒤 변수를 할당하는 식으로 사용할 수가 없었다. 결국 githubaction을 통해서 자동으로 FCM 인증서의 정보를 담은 json 파일을 만들어주고 그 파일을 마찬가지로 githubaction의 job을 통해 gradlew 빌드를해서 도커라이징을 한 뒤 쿠버네티스에 배포를 할 수가 있었다.

 

다음은 삽질을 하며 만든 githubaction의 workflows이다.

name: Build and Push Docker Image
on:
  push:
    branches:
      - main
jobs:
  build-and-push-image:
    env:
      IMAGE_TAG: ${{github.sha}}
    runs-on: ubuntu-latest
    steps:
      - name: Checkout
        uses: actions/checkout@v2

      - name: Set up JDK 17
        uses: actions/setup-java@v3
        with:
          java-version: '17'
          distribution: 'temurin'

      - name: check directory and change directory
        run: ls -al && cd ./src/main/resources && mkdir firebase && ls -al && cd firebase

      - name: create-json
        id: create-json
        uses: jsdaniell/create-json@v1.2.2
        with:
          name: "escort-8572e-firebase-adminsdk-6yrr0-c77a6887e1.json"
          json: ${{ secrets.FCM_JSON }}
          dir: 'src/main/resources/firebase/'

      - name: check FCM_directory and cat FCM_SECRET
        run: ls -al && cd ./src/main/resources/firebase && cat escort-8572e-firebase-adminsdk-6yrr0-c77a6887e1.json && ls -al

      - name : Build with Gradle
        run : ./gradlew build

      - name: Check build result
        run: |
          if [ -d build/libs ]; then
            echo "Contents of build/libs:"
              ls -al build/libs
          else
            echo "build/libs directory not found"
            exit 1
          fi



      - name: Set up Docker Buildx
        uses: docker/setup-buildx-action@v2

      - name: Login to DockerHub
        uses: docker/login-action@v1
        with:
          username: ${{ secrets.DOCKERHUB_USERNAME }}
          password: ${{ secrets.DOCKERHUB_TOKEN }}

      - name: Build and push
        id: docker_build
        uses: docker/build-push-action@v4
        with:
          context: .
          push: true
          tags: 'ggprgrkjh/kubernetes-spring-mysql-demo:${{env.IMAGE_TAG}}'
          platforms: |
            linux/arm64

      - name: Update image tag
        run: |
          sed -i 's|image: ggprgrkjh/kubernetes-spring-mysql-demo:test|image: 'ggprgrkjh/kubernetes-spring-mysql-demo:${{env.IMAGE_TAG}}'|' ./Resources/App/app-deployment.yaml
          cat ./Resources/App/app-deployment.yaml
        env:
          IMAGE_TAG: ${{github.sha}}

      - name: Check update image result
        run: |
          if [ -d ./Resources/App ]; then
            echo "Contents of ./Resources/App:"
              ls -al ./Resources/App
          else
            echo "./Resources/App directory not found"
            exit 1
          fi

      - name: change directory and delete unused FCM_SECRET
        run: ls -al && cd src/main/resources/firebase && rm -f escort-8572e-firebase-adminsdk-6yrr0-c77a6887e1.json && ls -al

      - name: Commit & Push change
        uses: actions-js/push@master
        with:
          github_token: ${{secrets.MY_GITHUB_TOKEN}}

 

 

순서를 간단하게 설명하면 다음과 같다.


1. github 레포지토리의 파일들을 받아온다.
2. JDK17버전으로 설정한다. (현재 스프링부트3버전을 쓰고 있기 때문)
3. 현재 로컬에서만 FCM인증서가 관리되고 있고 레포지토리에는 없기 때문에 ./src/main/resources로 이동해서 firebase 디렉토리를 만들어준다.
4. 마켓에 있는 -json 깃허브 액션 명령어를 사용해서 src/main/resources/firebase 위치에 json을 생성해준다. (그전에 깃허브 secret을 이용해서 secrets.FCM_JSON에 FCM설정 내용을 넣어줘야 한다.)
5. FCM 설정내용과 함께 gradlew build를 해서 jar파일로 만들어준다.
6. 도커 빌드를 buildx로 해준다. (m1 맥북 minikube arm 64 운영체제를 사용하고 있기 때문)
7. dockerhub에 로그인을 해준다.
8. 만들어진 JAR 파일을 이용해서 도커라이징을 한다.
9. docker hub에 push를 해준다
10. argo-cd의 동작을 위해서 연결된 디렉토리의 app-deployment.yaml의 이미지 태그를 최신화시켜준다.
11. 변경사항을 github에 올려준다.

Github Action을 사용해보면서 우여곡절이 많았고 그 덕에 프로젝트 커밋내역이 더러워졌지만 이 시간 덕분에 Github Action과 많이 친해질 수 있고 익숙해질 수 있는 계기가 되었던 것 같다. 그리고 막연하게만 생각했던 쿠버네티스 배포와 CI/CD를 직접 구축을 해 보니 자신감도 생기고 굉장히 뿌듯하다.


정상적으로 동작하는 CI/CD, Argo-CD 대시보드를 통해서 확인할 수 있다. (뿌듯)

 

 

 

삽질의 흔적과 결과