728x90
반응형

 

1. 액세스 토큰 생성

Personal Access Tokens (Classic) (github.com)  에서 패키지에 대한 권한을 가진 토큰을 생성한다.

생성되는 토큰 값을 저장한 뒤 원하는 곳에 txt 파일로 만들어두고, 아래 명령어 중 하나로 로그인 가능하다.

$ docker login https://ghcr.io -u outsideris // 입력 후 패스워드 토큰값 입력
$ cat TOKEN.txt | docker login https://ghcr.io -u outsideris --password-stdin

 

2. self_host runner를 만들고 등록해준다.

About self-hosted runners - GitHub Docs

 

About self-hosted runners - GitHub Docs

You can host your own runners and customize the environment used to run jobs in your GitHub Actions workflows.

docs.github.com

 

3. workflow를 만들어준다.

# This workflow uses actions that are not certified by GitHub.
# They are provided by a third-party and are governed by
# separate terms of service, privacy policy, and support
# documentation.
# This workflow will build a package using Gradle and then publish it to GitHub packages when a release is created
# For more information see: https://github.com/actions/setup-java/blob/main/docs/advanced-usage.md#Publishing-using-gradle

name: Workflow

permissions:
  contents: read
  packages: write
  checks: write

# 어떤 이벤트가 발생하면 workflow 실행할 지 명시
on:
  # main 브랜치에 pull_request 발생 시
  pull_request:
    branches:
      - main


# 위 이벤트 발생 시 실행될 작업들
jobs:
  # 빌드 후 Container Registry에 image 등록
  push_to_registry:
    # VM의실행 환경 지정 => self-hosted
    runs-on: self-hosted

    # 실행될 jobs 순서 대로 명시
    steps:
      - name: Checkout
        uses: actions/checkout@v4

      - name: Postgres Start
        env:
          ENV_FILE: ${{ secrets.ENV_FILE }}
        run: echo "$ENV_FILE" > ./.env &&
          docker image prune &&
          docker rm -f $(docker ps -qa) &&
          docker compose up db -d

      # JDK 17 설치
      - name: Set up JDK 17
        uses: actions/setup-java@v4
        with:
          java-version: '17'
          distribution: 'temurin'

      # Gradle Build를 위한 권한 부여
      - name: Grant execute permission for gradlew
        run: chmod +x ./gradlew

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

      # 테스트 결과를 PR에 코멘트로 달아줌
      - name: Publish test result
        uses: EnricoMi/publish-unit-test-result-action@v2.15.1
        if: always()
        with:
          files: '**/build/test-results/test/*.xml'

      # 테스트 실패 시 해당 코드 라인에 코멘트 달아줌.
      - name: When test fail, a comment is registered in the error code line.
        uses: mikepenz/action-junit-report@v4.1.0
        if: always()
        with:
          report_paths: '**/build/test-results/test/*.xml'

      # GitHub Container Registry 로그인
      - name: Login to GitHub Container Registry
        uses: docker/login-action@v3
        with:
          registry: ghcr.io
          username: ${{ secrets.GHUB_USERNAME }}
          password: ${{ secrets.GHUB_TOKEN }}

      # Docker image 빌드 및 push
      - name: Server Build and push
        uses: docker/build-push-action@v5
        with:
          context: .
          file: ./server/Dockerfile.prod
          push: true
          tags: ghcr.io/${{ secrets.GHUB_USERNAME }}/server:${{ secrets.RELEASE_VERSION }}

      - name: Client Build and push
        uses: docker/build-push-action@v5
        with:
          context: ./client
          file: ./client/Dockerfile.prod
          push: true
          tags: ghcr.io/${{ secrets.GHUB_USERNAME }}/client:${{ secrets.RELEASE_VERSION }}

      - name: Nginx Build and push
        uses: docker/build-push-action@v5
        with:
          context: ./docker/nginx
          push: true
          build-args: BUILD_ENV=prod
          tags: ghcr.io/${{ secrets.GHUB_USERNAME }}/nginx:${{ secrets.RELEASE_VERSION }}

      - name: DB Build and push
        uses: docker/build-push-action@v5
        with:
          context: ./docker/postgres
          push: true
          tags: ghcr.io/${{ secrets.GHUB_USERNAME }}/db:${{ secrets.RELEASE_VERSION }}

  # 서버에 배포
  deploy_via_ssh:
    needs: push_to_registry
    runs-on: self-hosted

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

      # Env 추가
      - name: Add Env
        env:
          ENV_FILE: ${{ secrets.ENV_FILE }}
          GHUB_USERNAME: ${{ secrets.GHUB_USERNAME }}
          RELEASE_VERSION: ${{ secrets.RELEASE_VERSION }}
        run: echo "$ENV_FILE" > ./.env &&
          echo -e "GHUB_USERNAME=$GHUB_USERNAME \nRELEASE_VERSION=$RELEASE_VERSION" >> ./.env

      # .env, docker-compose.prod.yml 파일 scp로 서버에 전송
      - name: copy files to target server via scp
        uses: appleboy/scp-action@v0.1.7
        with:
          host: ${{ secrets.DEPLOY_HOST }}
          username: ${{ secrets.DEPLOY_USERNAME }}
          key: ${{ secrets.DEPLOY_KEY }}
          port: ${{ secrets.DEPLOY_PORT }}
          source: ./docker-compose.prod.yml, ./.env
          target: /home

      #  원격으로 docker compose up 실행
      - name: remote docker-compose up via ssh
        uses: appleboy/ssh-action@v1.0.3
        with:
          host: ${{ secrets.DEPLOY_HOST }}
          username: ${{ secrets.DEPLOY_USERNAME }}
          key: ${{ secrets.DEPLOY_KEY }}
          port: ${{ secrets.DEPLOY_PORT }}
          envs: APPTOKEN,USERNAME
          script: |
            echo ${{ secrets.GHUB_TOKEN }} | sudo docker login ghcr.io --username ${{ secrets.GHUB_USERNAME }} --password-stdin &&
            cd /home &&
            sudo docker pull ghcr.io/${{ secrets.GHUB_USERNAME }}/server:${{ secrets.RELEASE_VERSION }} &&
            sudo docker pull ghcr.io/${{ secrets.GHUB_USERNAME }}/client:${{ secrets.RELEASE_VERSION }} &&
            sudo docker pull ghcr.io/${{ secrets.GHUB_USERNAME }}/db:${{ secrets.RELEASE_VERSION }} &&
            sudo docker pull ghcr.io/${{ secrets.GHUB_USERNAME }}/nginx:${{ secrets.RELEASE_VERSION }}

 

 

4. Dockefile

ghcr(컨테이너 레지스트리)에서 image를 pull 하므로 배포용 Docker 파일을 다음과같이 바꿔야 한다.

    app:
        image: ghcr.io/${IMAGE_REPO}:${RELEASE_VERSION}

 

5. secrets

github repository -> Settings -> Secrets and variables에서 secrets 항목들을 추가해준다.

참고로 github username은 반드시 소문자로 해야된다.


self-hosted 로 사용할 경우 서버의 사용자에 Docker 권한을 부여해주어야 한다.

 

How to fix docker: Got permission denied issue - Stack Overflow

 

How to fix docker: Got permission denied issue

I installed Docker in my machine where I have Ubuntu OS. When I run: sudo docker run hello-world All is ok, but I want to hide the sudo command to make the command shorter. If I write the command

stackoverflow.com

 

 

참고

GitHub Action Docker Compose deployments via SSH (servicestack.net)

 

728x90
반응형

+ Recent posts