-
Notifications
You must be signed in to change notification settings - Fork 0
234 lines (208 loc) ยท 8.81 KB
/
ci-cd.yml
File metadata and controls
234 lines (208 loc) ยท 8.81 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
name: Spring Boot CI/CD with AWS
on:
push:
branches: [ develop ]
pull_request:
types: [ opened, edited ]
branches: [ develop ]
permissions:
id-token: write
contents: write
pull-requests: write
checks: write
jobs:
build:
runs-on: ubuntu-latest
steps:
- name: Checkout Source Code
uses: actions/checkout@v4
- name: Set up JDK 17
uses: actions/setup-java@v4
with:
java-version: '17'
distribution: 'corretto'
# PR ํ
ํ๋ฆฟ ๊ฒ์ฌ
- name: Check PR Template
if: github.event_name == 'pull_request' && github.event.pull_request.body == ''
uses: actions/github-script@v7
with:
script: |
const fs = require('fs');
const template = fs.readFileSync('.github/pr_templates/for_develop.md', 'utf8');
github.rest.issues.createComment({
owner: context.repo.owner,
repo: context.repo.repo,
issue_number: context.issue.number,
body: `๐จ **PR ๋ณธ๋ฌธ์ด ๋น์ด์์ต๋๋ค!**\n\n์๋ ํ
ํ๋ฆฟ์ ๋ณต์ฌํ์ฌ PR ๋ด์ฉ์ ์์ฑํด์ฃผ์ธ์.\n\n---\n\n${template}`
});
core.setFailed('PR ๋ณธ๋ฌธ์ ํ
ํ๋ฆฟ์ ๋ง๊ฒ ์์ฑํด์ฃผ์ธ์.')
- name: Cache Gradle packages
uses: actions/cache@v3
with:
path: |
~/.gradle/caches
~/.gradle/wrapper
key: ${{ runner.os }}-gradle-${{ hashFiles('**/*.gradle*', '**/gradle-wrapper.properties') }}
restore-keys: |
${{ runner.os }}-gradle-
- name: Grant execute permission for gradlew
run: chmod +x ./gradlew
- name: Check code formatting (PR)
if: github.event_name == 'pull_request'
run: ./gradlew spotlessCheck
- name: Apply code formatting (Push)
if: github.event_name == 'push'
run: ./gradlew spotlessApply
- name: Create Pull Request with formatting changes
if: github.event_name == 'push'
id: create_pr
uses: peter-evans/create-pull-request@v6
with:
token: ${{ secrets.GITHUB_TOKEN }}
commit-message: "๐จ [BOT] Apply Spotless code style"
title: "๐จ [BOT] Apply Spotless code style"
body: |
Spotless ๋ด์ด ์ฝ๋ ์คํ์ผ์ ์๋์ผ๋ก ์์ ํ์ต๋๋ค.
๋ณ๊ฒฝ ์ฌํญ์ ํ์ธํ๊ณ ๋ณํฉํด ์ฃผ์ธ์.
*This PR was auto-generated by a GitHub Action.*
branch: "spotless-patches/${{ github.ref_name }}"
delete-branch: true
labels: bot, chore
- name: Build with Gradle
run: ./gradlew build --stacktrace --info
env:
R2_ENDPOINT: ${{ secrets.R2_ENDPOINT }}
R2_BUCKET: ${{ secrets.R2_BUCKET }}
R2_ACCESS_KEY: ${{ secrets.R2_ACCESS_KEY }}
R2_SECRET_KEY: ${{ secrets.R2_SECRET_KEY }}
R2_ACCOUNT_ID: ${{ secrets.R2_ACCOUNT_ID }}
JWT_SECRET: ${{ secrets.JWT_SECRET }}
FASTAPI_URL: ${{ secrets.FASTAPI_URL }}
API_TOKEN: ${{ secrets.API_TOKEN }}
check-ec2:
runs-on: ubuntu-latest
needs: build
if: github.event_name == 'push'
outputs:
ec2-available: ${{ steps.check-ec2-status.outputs.available }}
steps:
- name: Check EC2 instance status
id: check-ec2-status
run: |
if timeout 10 nc -z ${{ secrets.EC2_HOST }} 22 2>/dev/null; then
echo "EC2 instance is reachable"
echo "available=true" >> $GITHUB_OUTPUT
else
echo "EC2 instance is not reachable or stopped"
echo "available=false" >> $GITHUB_OUTPUT
fi
continue-on-error: true
build-and-push-image:
runs-on: ubuntu-latest
needs: [build, check-ec2]
if: github.event_name == 'push' && needs.check-ec2.outputs.ec2-available == 'true'
outputs:
image-pushed: ${{ steps.push-status.outputs.success }}
steps:
- name: Checkout Source Code
uses: actions/checkout@v4
- name: Configure AWS credentials using OIDC
uses: aws-actions/configure-aws-credentials@v4
with:
role-to-assume: ${{ secrets.AWS_ROLE_TO_ASSUME }}
aws-region: ${{ secrets.AWS_REGION }}
- name: Login to Amazon ECR
id: login-ecr
uses: aws-actions/amazon-ecr-login@v2
- name: Build, tag, and push image to Amazon ECR
id: build-image
env:
ECR_REGISTRY: ${{ steps.login-ecr.outputs.registry }}
ECR_REPOSITORY: cp_main_be
IMAGE_TAG: ${{ github.sha }}
run: |
docker build --no-cache -t $ECR_REGISTRY/$ECR_REPOSITORY:$IMAGE_TAG .
docker tag $ECR_REGISTRY/$ECR_REPOSITORY:$IMAGE_TAG $ECR_REGISTRY/$ECR_REPOSITORY:latest
docker push --all-tags $ECR_REGISTRY/$ECR_REPOSITORY
- name: Set push success status
id: push-status
if: success()
run: echo "success=true" >> $GITHUB_OUTPUT
deploy:
runs-on: ubuntu-latest
needs: [build, check-ec2, build-and-push-image]
if: github.event_name == 'push' && needs.build-and-push-image.outputs.image-pushed == 'true'
steps:
- name: Checkout Source Code
uses: actions/checkout@v4
- name: Configure AWS credentials using OIDC
uses: aws-actions/configure-aws-credentials@v4
with:
role-to-assume: ${{ secrets.AWS_ROLE_TO_ASSUME }}
aws-region: ${{ secrets.AWS_REGION }}
- name: Login to Amazon ECR
id: login-ecr
uses: aws-actions/amazon-ecr-login@v2
- name: Create Firebase Service Account Key File
env:
FIREBASE_KEY_JSON: ${{ secrets.FIREBASE_KEY_JSON }}
run: echo "$FIREBASE_KEY_JSON" > serviceAccountKey.json
- name: Create .env File
run: |
cat << EOF > ./.env
R2_ENDPOINT=${{ secrets.R2_ENDPOINT }}
R2_BUCKET=${{ secrets.R2_BUCKET }}
R2_ACCESS_KEY=${{ secrets.R2_ACCESS_KEY }}
R2_SECRET_KEY=${{ secrets.R2_SECRET_KEY }}
R2_ACCOUNT_ID= ${{ secrets.R2_ACCOUNT_ID }}
JWT_SECRET=${{ secrets.JWT_SECRET }}
FASTAPI_URL=${{ secrets.FASTAPI_URL }}
API_TOKEN=${{ secrets.API_TOKEN }}
DB_URL=${{ secrets.DB_URL }}
DB_USERNAME=${{ secrets.DB_USERNAME }}
DB_PASSWORD=${{ secrets.DB_PASSWORD }}
FIREBASE_KEY_JSON='${{ secrets.FIREBASE_KEY_JSON }}'
EOF
- name: Transfer necessary files to EC2
uses: appleboy/scp-action@master
with:
host: ${{ secrets.EC2_HOST }}
username: ${{ secrets.EC2_USER }}
key: ${{ secrets.EC2_SSH_KEY }}
# ๐ ์ ์ก ํ์ผ ๋ชฉ๋ก์์ .json ํ์ผ ์ญ์
source: "docker-compose.yml,.env"
target: "/home/${{ secrets.EC2_USER }}/app"
- name: Deploy to EC2 instance
uses: appleboy/ssh-action@master
with:
host: ${{ secrets.EC2_HOST }}
username: ${{ secrets.EC2_USER }}
key: ${{ secrets.EC2_SSH_KEY }}
script: |
cd /home/${{ secrets.EC2_USER }}/app
aws ecr get-login-password --region ${{ secrets.AWS_REGION }} | docker login --username AWS --password-stdin ${{ steps.login-ecr.outputs.registry }}
export ECR_REGISTRY=${{ steps.login-ecr.outputs.registry }}
# 1. ๊ธฐ์กด์ ์คํ ์ค์ธ ์ปจํ
์ด๋๋ฅผ ๋จผ์ ๋ด๋ฆฝ๋๋ค. (์ค์ง ๋ฐ ์ญ์ )
docker compose down
# 2. ์ต์ ์ด๋ฏธ์ง๋ฅผ ๋ฐ์์ต๋๋ค.
docker compose pull
# 3. ์๋ก์ด ์ปจํ
์ด๋๋ฅผ ์คํํฉ๋๋ค.
docker compose up -d --remove-orphans
summary:
runs-on: ubuntu-latest
needs: [build, check-ec2, build-and-push-image, deploy]
if: always()
steps:
- name: Workflow Summary
run: |
echo "## ์ํฌํ๋ก์ฐ ์คํ ๊ฒฐ๊ณผ" >> $GITHUB_STEP_SUMMARY
echo "| ๋จ๊ณ | ์ํ |" >> $GITHUB_STEP_SUMMARY
echo "|------|------|" >> $GITHUB_STEP_SUMMARY
echo "| ๋น๋ ๋ฐ ํ
์คํธ | ${{ needs.build.result == 'success' && 'โ
์ฑ๊ณต' || 'โ ์คํจ/๊ฑด๋๋' }} |"
if [[ "${{ github.event_name }}" == "push" ]]; then
echo "| EC2 ์ํ ํ์ธ | ${{ needs.check-ec2.result == 'success' && 'โ
์ฑ๊ณต' || (needs.check-ec2.result == 'skipped' && 'โญ๏ธ ๊ฑด๋๋' || 'โ ์คํจ') }} |"
echo "| Docker ์ด๋ฏธ์ง ๋น๋/ํธ์ | ${{ needs.build-and-push-image.result == 'success' && 'โ
์ฑ๊ณต' || (needs.build-and-push-image.result == 'skipped' && 'โญ๏ธ ๊ฑด๋๋' || 'โ ์คํจ') }} |"
echo "| EC2 ๋ฐฐํฌ | ${{ needs.deploy.result == 'success' && 'โ
์ฑ๊ณต' || (needs.deploy.result == 'skipped' && 'โญ๏ธ ๊ฑด๋๋' || 'โ ์คํจ') }} |"
else
echo "| ๋ฐฐํฌ ๊ด๋ จ ์์
| โญ๏ธ ๊ฑด๋๋ (PR ์ด๋ฒคํธ) |"
fi