AWS 페이지에서 CodeDeploy Service로 들어가 Application 생성을 누릅니다.
Application 이름을 입력해주고 플랫폼을 EC2/온프레미스로 설정해주고 생성해줍니다.
생성된 Application의 배포 그룹을 생성 해주기위해 배포 그룹 생성을 누릅니다.
배포 그룹의 이름을 입력하고 서비스를 수행할 수 있는 역할을 연결합니다. 여기서 이전 게시글에서 만든 CodeDeploy 역할을 선택합니다.
아래로 내려 환경 구성 탭에서 EC2 인스턴스를 클릭 후 배포하기위해 만든 EC2를 선택한 뒤 그룹을 생성해줍니다.
EC2에서 CodeDeploy agent로 배포하기위해 설정파일인 appspec.yml을 만들 것입니다.
root 바로 아래(build.gradle과 같은 위치)에 appspec.yml을 생성하고 아래 코드를 작성해줍니다.
version: 0.0
os: linux
files:
- source: /
destination: /home/ubuntu/{{target directory}}
overwrite: yes
permissions:
- object: /
pattern: "**"
owner: ubuntu
group: ubuntu
hooks:
ApplicationStart:
- location: deploy.sh
timeout: 60
runas: ubuntu
코드 내용(이해할 수 있는 정도로만 이해하였습니다.)
정확히 맞는지는 모르지만 EC2에 배포된 후의 작업들을 위한 설정을 해줍니다.
배포가 실행되면 EC2에 설치된 CodeDeploy agent에서 이 파일을 보고 받아온 프로젝트를 어디에 저장하고 무엇을 실행할 지 정하기 때문에 배포가 실행될 위치, 권한, 실행 hooks 설정 등을 이 파일에서 해주는 것 같습니다.
#!/usr/bin/env bash
# 기본은 /home/ubuntu로 하시면 되고 Ec2내에 폴더를 만들었으면 폴더 이름을 repository name에 넣어주세요
REPOSITORY=/home/ubuntu/{{ repository name }}
echo "> 현재 구동 중인 애플리케이션 pid 확인"
CURRENT_PID=$(pgrep -fla action | grep java | awk '{print $1}')
echo "현재 구동 중인 애플리케이션 pid: $CURRENT_PID"
if [ -z "$CURRENT_PID" ]; then
echo "현재 구동 중인 애플리케이션이 없으므로 종료하지 않습니다."
else
echo "> kill -15 $CURRENT_PID"
kill -15 $CURRENT_PID
sleep 5
fi
echo "> 새 애플리케이션 배포"
JAR_NAME=$(ls -tr $REPOSITORY/*.jar | tail -n 1)
echo "> JAR NAME: $JAR_NAME"
echo "> $JAR_NAME 에 실행권한 추가"
chmod +x $JAR_NAME
echo "> $JAR_NAME 실행"
nohup java -jar -Duser.timezone=Asia/Seoul $JAR_NAME >> $REPOSITORY/nohup.out 2>&1 &
코드 내용
실행중인 application이 있다면 PID를 잡아 종료시키고, jar 파일을 이용하여 nohup으로 무중단 배포를 진행해줍니다.
name: Java CI with Gradle
on:
push:
branches: [ main ]
pull_request:
branches: [ main ]
permissions:
contents: read
env:
S3_BUCKET_NAME: {{ 자신의 buck name }}
jobs:
build:
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v3
- name: Set up JDK 11
uses: actions/setup-java@v3
with:
java-version: '11'
distribution: 'temurin'
- name: Grant execute permission for gradlew
run: chmod +x gradlew
- name: Build with Gradle
uses: gradle/gradle-build-action@67421db6bd0bf253fb4bd25b31ebb98943c375e1
with:
arguments: build
- name: Make Directory
run: mkdir -p deploy
- name: Copy Jar
run: cp ./build/libs/*.jar ./deploy
- name: Copy appspec.yml
run: cp appspec.yml ./deploy
- name: Copy script
run: cp ./scripts/*.sh ./deploy
- name: Make zip file
run: zip -r ./{{zip 파일 이름}}.zip ./deploy
shell: bash
- name: Configure AWS credentials
uses: aws-actions/configure-aws-credentials@v1
with:
aws-access-key-id: ${{ secrets.AWS_ACCESS_KEY_ID }}
aws-secret-access-key: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
aws-region: ap-northeast-2
- name: Upload to S3
run: aws s3 cp --region ap-northeast-2 ./mylist.zip s3://$S3_BUCKET_NAME/
# Code Deploy 설정 추가
- name: Deploy
env:
AWS_ACCESS_KEY_ID: ${{ secrets.AWS_ACCESS_KEY_ID }}
AWS_SECRET_ACCESS_KEY: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
run: aws deploy create-deployment --application-name {{자신의 application 이름}} --deployment-group-name {{자신이 설정해준 group name}} --file-exists-behavior OVERWRITE --s3-location bucket={{자신의 bucket name}},bundleType=zip,key={{자신의 bucket zip 파일 이름}}.zip --region {{자신의 region (서울 : ap-northeast-2)}}
EC2의 Category 중 보안 그룹을 누르고 보안 그룹 생성을 누릅니다.
보안 그룹의 이름과 설명을 작성하고, 인바운드 규칙에서 자신의 server port에 맞춰 열어줍니다.(아래와 같이 열면 보안에 취약하지만 지금은 연습용이니 넘어갑니다.)
내 인스턴스로 가서 오른쪽 버튼을 누른 뒤 보안의 보안 그룹 변경으로 방금 만든 보안 그룹으로 지정해줍니다.
@RestController
public class HomeController {
@GetMapping("/")
public String home() {
return "hello home";
}
}
✒️ 참고
AWS codedeploy 에서 error가 발생한다면 여기를 참고하면 됩니다.
여기까지 진행하시면, github action을 이용한 spring boot project 배포가 끝납니다.
혹시나 작성 중 문제가 발생했다면, 제가 겪은 문제를 다음 게시글에 남겨두었으니 참고하시길 바랍니다.