AWS

[AWS] Github Action으로 빌드 파일 S3에 업로드하기 (CI/CD)

미소여우 2022. 4. 28. 09:18
728x90

 

바꾼 이유

이전에는 Docker를 통해 Spring boot를 빌드하고, docker hub에 이미지를 업로드하여 이를 EC2에서 올려 쓸까 생각했는데,

뭐랄까 EC2 하나를 쓰고(그것도 프리티어) 스케일 아웃도 할 생각도 없는데 배보다 배꼽이 큰 격이 되지 않을까 생각이 들었다.

물론 로컬 PC에서 테스트 환경 구성하기에 Docker-compose를 활용하면 최고라 생각하지만... 팀원들도 도커를 사용하기 어려워해서 일단은 잠시 내려두고 EC2에 바로 빌드된 파일만 올려 접근할 수 있도록 하기로 했다.

그렇다면 내가 일일히 빌드 파일을 EC2에 업로드 해야하지 않냐. 라는 의문이 들 수 있는데, 세상 정말 편리해졌다. Github Action을 잘 활용하면 나는 push만 하면 배포는 github action이 해준다. 지금부터 github action으로 s3에 업로드하는것을 보며, 나의 삽질 기록도 같이 하겠다.

CI/CD는 뭘까?

github action을 알기 전에 CI/CD를 간단히 이해해보자.

  • CI: Continuous Integration의 준말로 지속적 통합을 의미한다. 과거에는 빌드니 테스트니 개발자가 해주고, 검증해야했는데 이렇게 되면 분명 누락되는 부분도 발생하고, 실수도 하게 될 것이다. 이 문제는 프로젝트의 크기가 커질수록 비례하게 될 것이다. 그렇기에 이것을 잘 처리해주는 자동화 처리를 해두는 것이다. 자동화를 해두어 코드의 수정이나 병합이 일어났을 때(트리거) 테스트를 거치고 문제가 없으면 빌드를 해주는 것이다. 테스트가 실패하면 코드를 재검증하니 코드의 품질도 올라가는 효과도 같이 얻을 수 있다.
  • CD: Continuous Deployment의 준말로 지속적 배포를 의미한다. 결국 서비스를 갈아치우려면 서버에다가 새 코드를 올려야 하지 않는가. 이 또한 수동으로 한다는 것은 고욕이다. 그렇기에 CI 과정을 거쳐 문제가 없으면 내가 지정한 곳에 빌드된 파일을 올려 갈아치우면 배포가 끝나게 되는 것이다.

Github Action은?

위에서 언급한 CI/CD는 한 세트로 이해하면 될거 같고, 이것을 지원해주는 툴 중 하나가 Github Action이다! CI/CD 툴도 종류가 많은데 대표적으로 젠킨스(Jenkins)와 트래비스(Travis)가 있다. 젠킨스는 설치형 툴이기에 패스했고, 트래비스는 무료 버전이 있는데 카드도 등록하고 해야하는거 같아서 패스했다. 인터넷 글에서 사용자들의 경험을 보면 트래비스는 또 느린감이 있다고도 한다. 아무튼 Github Action은 public 레포지토리에 대해서는 무료고, 수 많은 개발자가 만들어둔 work들을 이용할 수 있기에 바로 이용해봤다.

정책에 대해서는 확실치 않으니 다른 글을 통해 알아봐주길 바란다. 또는 언젠가 정리하겠다. ㅎㅎ

 

사용법

Actions 화면

액션을 등록할 레포지토리에 들어가면 Actions 탭이 보일텐데 아래 Suggested for this repository를 지정하여 템플릿을 통해 쓸 수도 있고, 나는 set up a workflow yourself를 통해 수동으로 입력했다. (여기서부터 엄청난 삽질 시작..)

누르면 다음과 같이 화면이 뜬다.

보면 레포지토리/.github/workflows/ 디렉토리로 파일명.yml로 생성될 것이다. yml에 대해 궁금하다면 아래의 포스팅을 봐주면 되겠다.

 

[포맷 정리] YAML 문법 정리

도커를 쓰면서 docker-compose 파일을 작성하였는데, 이때 yml이라는 확장자로 설정 파일을 작성하게 된다. 그리고 스프링 부트에서도 외부 설정 파일로 application.properties와 application.yml로 작성할 수

somefood.tistory.com

먼저 완성본 코드를 보여주고 설명하겠다.

name: atk-action

on: 
  workflow_dispatch:

jobs: 
  build: 
    runs-on: ubuntu-18.04
    env:
      working-directory: ./server/stt-service
      resource_path: ./server/stt-service/src/main/resources/application-prod.yml

    steps: 
      - name: Checkout 
        uses: actions/checkout@v2 

      - name: Set up JDK 11
        uses: actions/setup-java@v1 
        with: 
          java-version: 11

      - name: Set yaml file
        uses: microsoft/variable-substitution@v1
        with:
          files: ${{ env.resource_path }}
        env:
          spring.datasource.url: ${{ secrets.RDS_URL }}
          spring.datasource.username: ${{ secrets.RDS_USERNAME }}
          spring.datasource.password: ${{ secrets.RDS_PASSWORD }}
          jwt.hash-key: ${{ secrets.JWT_HASH_KEY }}
          jwt.expire-time: ${{ secrets.JWT_EXPIRE_TIME }}
          jwt.subject: ${{ secrets.JWT_SUBJECT }}
          papago.secret: ${{ secrets.PAPAGO_SECRET }}
          papago.id: ${{ secrets.PAPAGO_ID }}
          oxford.app-id: ${{ secrets.OXFORD_ID }}
          oxford.app-key: ${{ secrets.OXFORD_KEY }}

      - name: Grant execute permission for gradlew 
        run: chmod +x gradlew
        working-directory: ${{ env.working-directory }}
        shell: bash 

      - name: Build with Gradle 
        run: ./gradlew build
        working-directory: ${{ env.working-directory }}
        shell: bash
        
      # 디렉토리 생성
      - name: Make Directory
        run: mkdir -p deploy
        working-directory: ${{ env.working-directory }}

      # Jar 파일 복사
      - name: Copy Jar
        run: cp ./build/libs/*.jar ./deploy
        working-directory: ${{ env.working-directory }}

      # 파일 압축
      - name: Make zip file
        run: zip -r ./springboor-with-githubaction.zip ./deploy
        working-directory: ${{ env.working-directory }}

      # Deploy
      - name: Deploy
        uses: aws-actions/configure-aws-credentials@v1
        with:
          aws-access-key-id: ${{ secrets.AWS_ACCESS_KEY }}
          aws-secret-access-key: ${{ secrets.AWS_SECRET_KEY }}
          aws-region: ap-northeast-2

      - name: Upload to S3
        run: aws s3 cp --region ap-northeast-2 ./springboor-with-githubaction.zip s3://atkproject-bucket/springboot-with-githubaction.zip
        working-directory: ${{ env.working-directory }}
  • name: action의 이름 정도
  • on: 트리거를 정하는 것이다. 예로 들면 main 브랜치로 push가 되면 동작시킬 수도 있는데, 나는 아직 테스트해볼게 많아 수동으로 등록하기 위해 workflow_dispatch를 지정했다.
  • jobs: 액션이 작동되면 일을 시작해야지 않는가? 어떤 일들을 할 건지 정해주는 부분이라 보면 되겠다.
  • runs-on: 어떤 OS 기반에서 실행시킬건지 정하는 건데, 필자의 경우 EC2 운영체제랑 맞춰 주었다.
  • env: 환경변수들 지정
    • working-directory: 어떤 디렉토리에서 작업할 건지 지정. 단순히 스프링 프로젝트만 올리면 없어도 되는데, 우리 팀의 repository의 구조는 클라이언트와 서버 내용이 있어 계층화가 좀 더 되어있다. 이러면 내가 작업할 위치를 지정해주지 않으면 엄청난 에러를 맛 볼 것이다. (1차 삽질..)
    • resource_path: 스프링에서 profile.. dev용 prod용을 나누었는데 여기서 또 문제가 prod용에서 시크릿 키들은 gitignore를 시켜두었다. 이러면 빌드 시 파일들을 못 찾아 또 눈물을 맛 보기 때문에, 해결해주려고 썼다.
  • steps: 스텝을 정하여 단계별로 진행해준다.
  • uses: actions/checkout@2: 내 레포지토리 내용들을 접근할 수 있게 해준다. runs-on의 우분투에서 내 파일들을 활용해야 무언가 작업할 수 있으니 꼭 필요
  • actions/setup-java@1: java 11버전을 사용하기 위해 사용
  • microsoft/variable-substitution@v1: 파일의 내용을 치환시키기 위해 사용했다. 내 애플리케이션 설정 내용들을 github의 시크릿 키에서 넣어주기 위해 썼다. (여기서 정말 많은 시간을 할애했다.. 스프링 프로필 분리는 추후에 업로드 하겠다.)
    • env: 여기서 치환할 키 값의 value들을 치환 해주었다. ${{ secrets.XXX }} 들은 시크릿 키를 갖고 올 때 쓴다
  • 이후 주석의 #디렉토리 생성 전까지 자바 빌드하는 과정이다. 여기서 정말 많은 실패를 겪게 되었다... 그 다음은 대망의 S3에 등록하는 과정이다.
  • 디렉토리를 생성하고, .jar파일을 복사하고 압축하였다. 압축한 이유는 .jar파일로 바로 업로드 되지 않아서 zip으로 바꾸어 올린 것이다.
  • Deploy 할 시 내 S3와 관련된 시크릿 키들을 등록해야 한다.
  • 그리고 최종적으로 마지막 명령을 통해 S3 파일이 업로드 된다.

S3 등록은 여기선 너무 방대하니 다른 글에서 올려보도록 하겠다. 또는 아래 참고에 있는 링크들을 봐주면 되겠다.

깃헙에 시크릿 키들은 아래와 같이 등록해주면 된다.

Settings -> Secrets -> Actions에 들어가 New repository secret을 클릭하여 적절한 이름과 비밀키들을 넣어주면 된다.

참고

 

Azure에 대한 GitHub Actions에서 변수 바꾸기 사용

매개 변수가 있는 파일의 변수를 바꾸는 GitHub Action

docs.microsoft.com

 

 

Github Action을 사용하여 빌드시 동적으로 변숫값 주입하기 (feat. Dynamic Variable Substitution)

Index

goodgid.github.io

 

Github Actions + CodeDeploy + Nginx 로 무중단 배포하기 (1)

개요 안녕하세요! 이번 시리즈에서는 제목에서와 같이 Github Actions 와 CodeDeploy, 그리고 Nginx 를 사용하여 하나의 서버에서 최소 규모의 무중단 배포를 진행하는 방법에 대해 정리해보려고 합니다.

wbluke.tistory.com

 

728x90