ν΄λΉ μ리μ¦λ 3κ°μ κΈλ‘ ꡬμ±λμ΄μμ΅λλ€. κ° λ¨κ³μ μμΈν μ¬νμ μλ λ§ν¬λ₯Ό μ°Έμ‘°ν΄μ£ΌμΈμ
- 1νΈ Spring Boot μλ² μμ±νκΈ°
- 2νΈ Elastic Beanstalk μμ±νκΈ°
- 3νΈ Github Actions μ μνκΈ°
- ν΄λΉ κΈμ μ€μ΅ μ½λ λ° github repository
μ§λ μκ°...
μ§λ μκ° μ°λ¦¬λ Spring Boot λ₯Ό μ΄μ©ν΄μ Application μλ²λ₯Ό μμ±νκ³ Elastic Beanstalk λ₯Ό μμ± νλ€.
μ΄λ² μκ°μλ Github Actions λ₯Ό μ΄μ©νμ¬ Master branch μ λ³κ²½μ¬νμ΄ μλ€λ©΄ μλμΌλ‘ λ°°ν¬νλ λ°°ν¬ μλνμ λν΄μ μμ보μ.
Github Actions μ λν΄μ λ μμΈν
Github Actions λ κΉνλΈμμ 곡μμ μΌλ‘ μ 곡νλ workflow μλν ν΄μ΄λ€
Workflow μλνλΌκ³ νλ€λ©΄ Continous Delivery, Deploy μΈ CD μ λν΄μ μ΄μΌκΈ°κ° μμ£Ό λμ€μ§λ§ μ΄λ€μ μμ°ν λ€λ₯Έ λΆλ₯λΌκ³ νλ€.
μ΄μ λν λ΄μ©μ μΆνμ λ 곡λΆνκ³ λ€λ€λ³΄κΈ°λ‘ νκ³ Github Actions μμ μ¬μ©νλ κ°λ λ€μ΄ μλ€ νγ λ μμ보μ.
Github Actions μ κ°λ
- Workflow
- μλνλ μ 체 νλ‘μΈμ€λ‘ νλ μ΄μμ Job μΌλ‘ ꡬμ±λλ©° Event μ μν΄ νΈλ¦¬κ±° λκ±°λ μμ½λ μ μλ€.
- λ°°ν¬λ₯Ό ν¬ν¨νμ¬ ν μ€νΈ, infra ꡬμ±λ± λͺ¨λ νλλ‘ λ³΄λ κ°λ μ΄λ€.
- Jenkins μ Pipeline κ³Ό λΉμ·ν κ°λ μ΄λ€.
- Event
- Workflow λ₯Ό νΈλ¦¬κ±°νλ νΉμ ν νλμ΄λ κ·μΉμ΄λ€.
- λ³΄ν΅ master, main, release λΈλμΉμ νΈλ¦¬κ±° κ·μΉμ μ ν΄λκ³€ νλ€.
- μ¦, master λΈλμΉμ μ½λ λ³κ²½μ¬νμ΄ μλ€λ©΄ Workflow λ₯Ό λ°λμν¨λ€.
- Job
- λ¨μΌ κ°μ νκ²½μμ μ€νλλ μμ λ€μ λ¨μμ΄λ€.
- μ¬λ¬ Jobκ³Ό μμ‘΄ κ΄κ³λ₯Ό λ§Ίμ μ μμΌλ©° λ 립, λ³λ ¬λ‘ μ€νλ μ μλ€.
- Step
- Job μμμ μμ°¨μ μΌλ‘ μ€νλλ νλ‘μΈμ€ λ¨μμ΄λ€.
- Action
- job μ ꡬμ±νκΈ° μν step μ μ‘°ν©μ΄λ€.
- Github Actions Marcket Place μ λ§μ Actions κ° μ μλμ΄ μμ΄μ μ½κ² κ°μ Έλ€ μ¬μ©ν μ μλ€.
- Runner
- Github Action Runner κ° μ€μΉλ λ¨Έμ μΌλ‘ Workflow κ° μ€νλ μΈμ€ν΄μ€λ₯Ό μλ―Ένλ€
Github Action μμ±νκΈ°
Github Actions λ₯Ό μμ±νλ λ°©λ²μ λ§€μ° κ°λ¨νλ€.
Project Repository μ .github/workflows
λλ ν 리λ₯Ό μμ±νκ³ yml ν¬λ§·μ νμΌλ‘ Workflow λ₯Ό μ μν΄μ£Όλ©΄ λμ΄λ€.
μ°λ¦¬κ° μμ μμ±ν νλ‘μ νΈ λ ν¬μ§ν 리μ λ€μκ³Ό κ°μ κ΅¬μ‘°λ‘ λλ ν 리μ νμΌμ μμ±ν΄λ³΄μ
todo-master-deploy.yml
name: todo-master-to-beanstalk
on:
push:
branched:
- master # action νΈλ¦¬κ±° λΈλμΉ
workflow_dispatch: # μλ μ€ν μ΅μ
(μλ΅)
jobs:
build:
runs-on: ubuntu-latest # action μ€ν¬λ¦½νΈκ° μλλ OS
steps: # μμ
λ¨κ³
- name: Checkout source code # λ¨κ³λ³ μ΄λ¦, ꡬλΆμλ‘ μμ€λ₯Ό κ°μ Έμ΄
uses: actions/checkout@v2
- name: Set up JDK 1.8 # JDK μ€μΉ
uses: actions/setup-java@v1 # (5)
with:
java-version: 1.8
- name: Grant execute permission for gradlew
working-directory: ./server-app
run: chmod +x ./gradlew
shell: bash
- name: Build with Gradle
working-directory: ./server-app
run: ./gradlew clean build
shell: bash
- name: Get current time
uses: 1466587594/get-current-time@v2
id: current-time
with:
format: YYYYMMDDTHHmm
utcOffset: "+09:00"
- name: Generate deployment package
run: |
mkdir -p deploy
cp server-app/build/libs/server-app.jar deploy/todo-application-prod-ebextensions-1.jar
cp Procfile deploy/Procfile
cp -r .ebextensions deploy/.ebextensions
cd deploy && zip -r todo-application-prod-label-${{steps.current-time.outputs.formattedTime}}-${{github.sha}} .
- name: Deploy Consumer to EB
uses: einaregilsson/beanstalk-deploy@v14
with:
aws_access_key: ${{ secrets.AWS_ACCESS_KEY_ID }}
aws_secret_key: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
application_name: todo-application-prod
environment_name: Todoapplicationprod-env
version_label: todo-application-prod-label-${{steps.current-time.outputs.formattedTime}}-${{github.sha}}
region: ap-northeast-2
deployment_package: deploy/todo-application-prod-label-${{steps.current-time.outputs.formattedTime}}-${{github.sha}}.zip
λκ° λ§€μ° λ§κ³ ν·κ°λ¦°λ€.
νμ§λ§ κ±±μ ν κ²μ΄ μ ν μλ€.
μμ μ΄μΌκΈ°νλ― κ°κ°μ Job μ μ€νμν€λ λ°©λ²λ€μ λͺ μΈν΄λμ κ²μ΄κ³ μ΄λ€μ λͺ¨λ μΈμ°κ³ μμ§ μμλ Marcket Place μμ μ½κ² 볡μ¬νμ¬ λΆμ¬λ£μΌλ©΄ λλ€.
κ·ΈλΌ μκΉ μ΄μΌκΈ° νλ Github Actions μ κ°λ μ μ μ©ν΄μ μ΄λ€ κ΅¬μ‘°λ‘ yml μ΄ κ΅¬μ±λμ΄μλμ§ μμ보μ.
μμ yml μ μκ² λΆν΄ν΄λ³΄κ² λ€.
Workflow μ μ
name: todo-master-to-beanstalk
on:
push:
branched:
- master # action νΈλ¦¬κ±° λΈλμΉ
workflow_dispatch: # μλ μ€ν μ΅μ
(μλ΅)
jobs:
build:
runs-on: ubuntu-latest # action μ€ν¬λ¦½νΈκ° μλλ OS
ν΄λΉ workflow λ todo-master-to-beanstalk
λΌλ μ΄λ¦μ workflow μ΄λ€.
master λΈλμΉλ‘ push λλ€λ©΄ μ΄λ²€νΈλ₯Ό λ°μμν€κ³ workflow_distpatch
λ μλ΅νμλλ°, μ΄λ μλμΌλ‘ μ€νν λ μ£Όλ μ΅μ
κ°μ΄λ€.
λν Job μ΄ μ€νλ OS λ ubuntu μμ μ€νμ΄ λλ€λ κ²μ μ μ μλ€.
Job μ μ - 1. source code
- name: Checkout source code # λ¨κ³λ³ μ΄λ¦, ꡬλΆμλ‘ μμ€λ₯Ό κ°μ Έμ΄
uses: actions/checkout@v2
μμ step λΈλ‘μ ν΄λΉ Workflow κ° λ ν¬μ§ν 리μ μ‘μΈμ€ν μ μλλ‘ μ¬μ©λλ 곡μ Action μ΄λ€.
Job μ μ - 2. JDK μ€μΉ
- name: Set up JDK 1.8 # JDK μ€μΉ
uses: actions/setup-java@v1 # (5)
with:
java-version: 1.8
보면 λ°λ‘ μ μ μλ― JDK Action μ κ°μ Έμ μ€ννλ€.
JDK λ²μ μ 1.8 λ²μ μΌλ‘ Java8 μ μ¬μ©νλ€.
Job μ μ - 3. Gradle μ€μ
- name: Grant execute permission for gradlew
working-directory: ./server-app
run: chmod +x ./gradlew
shell: bash
- name: Build with Gradle
working-directory: ./server-app
run: ./gradlew clean build
shell: bash
ν΄λΉ λΈλμ Gradle κ³Ό κ΄λ ¨λ μ€μ μ΄λ€.
chmod λ₯Ό ν΅ν΄μ Application Server λλ ν 리μ gradlew μκ² μ€ν κΆνμ λΆμ¬νκ³ μ±μ build νλ€.
working-directory λ₯Ό μ΄μ©ν΄μ ./server-app
μ΄ μμ
μ μνν λλ ν 리μμ λͺ
μνμλ€.
Job μ μ - 4. μκ° μ€μ
- name: Get current time
uses: 1466587594/get-current-time@v2
id: current-time
with:
format: YYYYMMDDTHHmm
utcOffset: "+09:00"
μλ²λ₯Ό λ°°ν¬ν λλ μλ²μ λ²μ λμ΄ λ§€μ° μ€μνλ€.
μ΄ λ²μ λμ μν΄μ get-current-time μ΄λΌλ Action μ κ°μ Έμ μ¬μ©νλΌλ λΈλμ΄λ€.
Job μ μ - 5. λ°°ν¬ μ€μ
- name: Generate deployment package
run: |
mkdir -p deploy
cp server-app/build/libs/server-app.jar deploy/todo-application-prod-ebextensions-1.jar
cp Procfile deploy/Procfile
cp -r .ebextensions deploy/.ebextensions
cd deploy && zip -r todo-application-prod-label-${{steps.current-time.outputs.formattedTime}}-${{github.sha}} .
μ΄ Job μ΄ νμ¬ κ΅¬μ±ν Actions μ μλ€ μ€ κ°μ₯ κΉλ€λ‘μ΄ λΆλΆμ΄λ€.
μ°μ λμ΄κ°κ³ μλμμ μμΈν μμ보μ
Job μ μ - 6. Elastic Beanstalk Consumer μ°κ²°
- name: Deploy Consumer to EB
uses: einaregilsson/beanstalk-deploy@v14
with:
aws_access_key: ${{ secrets.AWS_ACCESS_KEY_ID }}
aws_secret_key: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
application_name: todo-application-prod
environment_name: Todoapplicationprod-env
version_label: todo-application-prod-label-${{steps.current-time.outputs.formattedTime}}-${{github.sha}}
region: ap-northeast-2
deployment_package: deploy/todo-application-prod-label-${{steps.current-time.outputs.formattedTime}}-${{github.sha}}.zip
Beanstalk λ₯Ό μ°κ²°νλ λΆλΆμ΄λ€.
μ¬κΈ°μ μμ μ μν EBμ Application μ΄λ¦κ³Ό environment μ΄λ¦μ μ€μ νκ³ SECRET μ ν΅ν΄ μ°κ²°ν΄μ€λ€.
μ΄μ μ μ 5λ² 6λ²μ λν΄μ μμΈν μμ보μ.
λ°°ν¬ μ€μ μμΈν 보기 - Procfile
Procfile μ Elastic Beanstalk μκ² μ€νν JAR λ₯Ό μλ €μ£Όλ νλ‘μΈμ€ κ΅¬μ± νμΌμ΄λ€.
νλ‘μ νΈ λ£¨νΈμ Procfile
νμΌμ μμ±νμ.
κ·Έλ¦¬κ³ ν΄λΉ νμΌμ web λΈλμ μ€νν jar νμΌμ μΆκ°μμΌμ£Όλ©΄ λλ€.
web: java -jar todo-application-prod-ebextensions-1.jar
μ°λ¦¬μ μλ²λ₯Ό ν¨ν€μ§νλ©΄ 2κ°μ jar νμΌμ΄ μμ±λλλ°, EBμμλ μ΄λ€ jar νμΌμ μ€νμμΌμΌνλμ§ λͺ¨λ₯΄κΈ° λλ¬Έμ μμ κ°μ΄ Procfile μ μμ±ν΄μ£Όκ³ EB λ΄λΆλ‘ λ£μ΄μ€μΌ νλ€.
λ°°ν¬ μ€μ μμΈν 보기 - ebextensions
.ebextenstions
λ config νμΌμ μ΄μ©ν΄μ κ³ κΈ νκ²½ ꡬμ±μ ν μ μλλ‘ νλ€.
Timezone μ€μ μ μν΄ μ¬μ©νμλλ°, μ΄ μμ EB λ΄λΆλ‘ λ£μ΄μ£Όμ΄μΌ νλ€.
commands:
set_time_zone:
command: ln -f -s /usr/share/zoneinfo/Asia/Seoul /etc/localtime
Consumer μμΈν 보기 - Github Secret μ€μ
Job μ μ 6λ² μ λ€μ λ΄λ³΄μ
- name: Deploy Consumer to EB
uses: einaregilsson/beanstalk-deploy@v14
with:
aws_access_key: ${{ secrets.AWS_ACCESS_KEY_ID }}
aws_secret_key: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
application_name: todo-application-prod
environment_name: Todoapplicationprod-env
version_label: todo-application-prod-label-${{steps.current-time.outputs.formattedTime}}-${{github.sha}}
region: ap-northeast-2
deployment_package: deploy/todo-application-prod-label-${{steps.current-time.outputs.formattedTime}}-${{github.sha}}.zip
aws_access_key
μ aws_secret_key
λ₯Ό 보면 μ€μ κ°μ λ
ΈμΆμν€λ κ²μ΄ μλλΌ μΈλΆ μ€μ μμ κ°μ Έμ€κ³ μλ€.
μ΄λ₯Ό μν΄μ Repository Setting μμ Key λ₯Ό λ±λ‘μμΌμ£Όμ.
Repository μ Setting μμ Secret νμ λ€μ΄κ°μ μλ‘μ΄ Action Secret μ μμ±ν΄μ£Όμ
μμ μμ±ν IAM μ Access μ Secret μ λ±λ‘ν΄μ£Όλ©΄ λλ€.
κ·ΈλΌ μμ Job μ μ 6λ²μμ μΈλΆ μ€μ μ κ°μ Έμ¬ μ μκ² λλ€.
μ½λ νΈμνμ¬ Actions μ EB μ°κ²°νκΈ°
μ΄μ λͺ¨λ μ€λΉκ° λ€ λμλ€!
github μ master λΈλμΉλ‘ push νμ¬ EBλ₯Ό Trigger ν΄λ³΄μ
κ·ΈλΌ μμ κ°μ΄ λκΈ°μ€μ΄ λ¨λ©° κ²°κ΅μ Success κ° λ€μ΄μ€κ² λλ©° μλ‘μ΄ λ²μ μΌλ‘ μ λμνλ κ²μ μ μ μλ€.
λκΈ