Deploy #419
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| name: Deploy | |
| on: | |
| push: | |
| branches: | |
| - fix/** | |
| workflow_run: | |
| workflows: ["CI (Java)"] | |
| types: [completed] | |
| jobs: | |
| deploy: | |
| name: Deploy to AWS EC2 | |
| runs-on: ubuntu-latest | |
| if: | | |
| github.event.workflow_run.conclusion == 'success' && | |
| startsWith(github.event.workflow_run.head_branch, 'user-service-v') | |
| steps: | |
| - uses: actions/checkout@v4 | |
| - name: Create env file and config folder | |
| run: | | |
| echo "DB_HOST=${{ secrets.DB_HOST }}" > .env.prod | |
| echo "DB_PORT=${{ secrets.DB_PORT }}" >> .env.prod | |
| echo "DB_USER=${{ secrets.DB_USER }}" >> .env.prod | |
| echo "DB_PASS=${{ secrets.DB_PASS }}" >> .env.prod | |
| echo "DB_NAME=${{ secrets.DB_NAME }}" >> .env.prod | |
| echo "LOKI_HOST=${{ secrets.LOKI_HOST }}" >> .env.prod | |
| echo "LOKI_USERNAME=${{ secrets.LOKI_USERNAME }}" >> .env.prod | |
| echo "LOKI_PASSWORD=${{ secrets.LOKI_PASSWORD }}" >> .env.prod | |
| echo "ENV_NAME=${{ secrets.ENV_NAME }}" >> .env.prod | |
| echo "FASTAPI_SERVER_HOST=${{ secrets.FASTAPI_SERVER_HOST }}" >> .env.prod | |
| echo "GRAFANA_CLOUD_PROMETHEUS_URL=${{ secrets.GRAFANA_CLOUD_PROMETHEUS_URL }}" >> .env.prod | |
| echo "GRAFANA_CLOUD_PROMETHEUS_USER=${{ secrets.GRAFANA_CLOUD_PROMETHEUS_USER }}" >> .env.prod | |
| echo "GRAFANA_CLOUD_API_KEY=${{ secrets.GRAFANA_CLOUD_API_KEY }}" >> .env.prod | |
| echo "MAIL_USERNAME=${{ secrets.MAIL_USERNAME }}" >> .env.prod | |
| echo "MAIL_PASSWORD=${{ secrets.MAIL_PASSWORD }}" >> .env.prod | |
| # Create config folder and copy config files | |
| mkdir -p config | |
| cp apps/user-service/src/main/resources/application-production.yml config/ | |
| cp apps/user-service/src/main/resources/log4j2-production.yml config/ | |
| - name: Set repo lowercase | |
| run: echo "REPO_LC=${GITHUB_REPOSITORY,,}" >> $GITHUB_ENV | |
| - name: Copy docker compose files to EC2 | |
| uses: appleboy/[email protected] | |
| with: | |
| host: ${{ secrets.SERVER_HOST }} | |
| username: ubuntu | |
| key: ${{ secrets.SERVER_SSH_KEY }} | |
| source: "docker/production/docker-compose.yml" | |
| target: "~/app" | |
| overwrite: true | |
| - name: Copy .env.prod file to EC2 | |
| uses: appleboy/[email protected] | |
| with: | |
| host: ${{ secrets.SERVER_HOST }} | |
| username: ubuntu | |
| key: ${{ secrets.SERVER_SSH_KEY }} | |
| source: ".env.prod" | |
| target: "~/app/docker/production/" | |
| overwrite: true | |
| - name: Copy Caddyfile to EC2 | |
| uses: appleboy/[email protected] | |
| with: | |
| host: ${{ secrets.SERVER_HOST }} | |
| username: ubuntu | |
| key: ${{ secrets.SERVER_SSH_KEY }} | |
| source: "docker/production/Caddyfile" | |
| target: "~/app" | |
| overwrite: true | |
| - name: Copy promtail-config to EC2 | |
| uses: appleboy/[email protected] | |
| with: | |
| host: ${{ secrets.SERVER_HOST }} | |
| username: ubuntu | |
| key: ${{ secrets.SERVER_SSH_KEY }} | |
| source: "docker/production/promtail-config.yml" | |
| target: "~/app" | |
| - name: Copy agent-config to EC2 | |
| uses: appleboy/[email protected] | |
| with: | |
| host: ${{ secrets.SERVER_HOST }} | |
| username: ubuntu | |
| key: ${{ secrets.SERVER_SSH_KEY }} | |
| source: "docker/production/agent-config.yml" | |
| target: "~/app" | |
| overwrite: true | |
| - name: Copy application-production.yml to EC2 | |
| uses: appleboy/[email protected] | |
| with: | |
| host: ${{ secrets.SERVER_HOST }} | |
| username: ubuntu | |
| key: ${{ secrets.SERVER_SSH_KEY }} | |
| source: "config/application-production.yml" | |
| target: "~/app/docker/production/" | |
| overwrite: true | |
| - name: Copy log4j2-production.yml to EC2 | |
| uses: appleboy/[email protected] | |
| with: | |
| host: ${{ secrets.SERVER_HOST }} | |
| username: ubuntu | |
| key: ${{ secrets.SERVER_SSH_KEY }} | |
| source: "config/log4j2-production.yml" | |
| target: "~/app/docker/production/" | |
| overwrite: true | |
| - name: Deploy on EC2 | |
| uses: appleboy/[email protected] | |
| with: | |
| host: ${{ secrets.SERVER_HOST }} | |
| username: ubuntu | |
| key: ${{ secrets.SERVER_SSH_KEY }} | |
| script: | | |
| cd ~/app/docker/production | |
| echo "${{ secrets.GITHUB_TOKEN }}" | docker login ghcr.io -u ${{ github.actor }} --password-stdin | |
| # 최신 이미지 pull | |
| docker-compose pull | |
| # 기존 컨테이너 종료 및 제거 | |
| docker-compose down | |
| # 새 컨테이너 배포 | |
| docker-compose up -d | |
| # 컨테이너 상태 확인 | |
| sleep 5 | |
| docker-compose ps | |
| # 헬스 체크 (컨테이너가 healthy 상태가 될 때까지 대기) | |
| echo "Waiting for containers to become healthy..." | |
| for i in {1..30}; do | |
| unhealthy=$(docker ps --filter "health=unhealthy" --format "{{.Names}}") | |
| starting=$(docker ps --filter "health=starting" --format "{{.Names}}") | |
| if [ -z "$unhealthy" ] && [ -z "$starting" ]; then | |
| echo "All containers are healthy!" | |
| break | |
| fi | |
| echo "Waiting... ($i/30)" | |
| sleep 2 | |
| done | |
| # 사용하지 않는 dangling 이미지 정리 | |
| docker image prune -f | |
| - name: Send Discord notification - Success | |
| if: success() | |
| uses: Ilshidur/action-discord@master | |
| env: | |
| DISCORD_WEBHOOK: ${{ secrets.DISCORD_WEBHOOK_URL }} | |
| with: | |
| args: | | |
| **배포 성공** | |
| **Repository:** ${{ env.REPO_LC }} | |
| **Tag:** ${{ github.ref_name }} | |
| **Server:** ${{ secrets.SERVER_HOST }} | |
| **Status:** Success! | |
| - name: Send Discord notification - Failure | |
| if: failure() | |
| uses: Ilshidur/action-discord@master | |
| env: | |
| DISCORD_WEBHOOK: ${{ secrets.DISCORD_WEBHOOK_URL }} | |
| with: | |
| args: | | |
| **배포 실패** | |
| **Repository:** ${{ env.REPO_LC }} | |
| **Tag:** ${{ github.ref_name }} | |
| **Error:** 배포 중 오류가 발생했습니다. | |
| **Check:** ${{ github.server_url }}/${{ github.repository }}/actions/runs/${{ github.run_id }} |