Jenkins & docker CI/CD 파이프라인
지난 포스팅에서는 docker 위에서 실행되는 Jenkins를 활용해서 Spring Boot 애플리케이션을 배포했다.
이번에는 Jenkins환경은 같지만, Docker에서 실행되는 Spring Boot 어플리케이션에 대해서 CI/CD 파이프라인을 구축해 보겠다.
EC2 서버에 Docker 설치
Docker
sudo apt-get update
sudo apt-get install ca-certificates curl gnupg
sudo install -m 0755 -d /etc/apt/keyrings
curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo gpg --dearmor -o /etc/apt/keyrings/docker.gpg
sudo chmod a+r /etc/apt/keyrings/docker.gpg
echo \
"deb [arch="$(dpkg --print-architecture)" signed-by=/etc/apt/keyrings/docker.gpg] https://download.docker.com/linux/ubuntu \
"$(. /etc/os-release && echo "$VERSION_CODENAME")" stable" | \
sudo tee /etc/apt/sources.list.d/docker.list > /dev/null
Docker Engine
sudo apt-get update
sudo apt-get install docker-ce docker-ce-cli containerd.io docker-buildx-plugin docker-compose-plugin
sudo chmod 006 /var/run/docker.sock
docker -v
Docker에서 Jenkins 설치 및 실행
Jenkins 설치
docker pull jenkins/jenkins:jdk11
docker images
ubuntu@ip-172-31-12-140:~$ docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
jenkins/jenkins jdk11 541ec44c40ea 5 days ago 463MB
Jenkins 실행
docker run -d \
--name jenkins \
-p 80:8080 \
-v /var/run/docker.sock:/var/run/docker.sock \
jenkins/jenkins:jdk11
- -d: detached mode로 실행 (백그라운드)
- --name: 컨테이너 이름 지정
- -v: 호스트와 컨테이너 간 디렉터리 또는 파일 매핑 설정
Spring boot Jenkins 파이프라인 생성
Jenkinsfile
pipeline {
agent any
stages {
stage('Git clone') {
steps {
git branch: '${branchName}',
url: '${repository url.git}'
}
}
stage ("build") {
steps {
sh "chmod +x gradlew"
sh "cp ../settings/application.yml src/main/resources"
sh "./gradlew clean build"
}
}
stage ("docker login") {
steps {
sh "echo $DOCKER_HUB_PASSWORD | docker login -u $DOCKER_HUB_USERNAME --password-stdin"
}
}
stage ("docker build") {
steps {
sh "docker build . -t {dockerhubUsername/imageName:tag}"
}
}
stage ("docker push") {
steps {
sh "docker push {dockerhubUsername/imageName:tag}"
}
}
stage ("docker clear") {
steps {
sh "docker rmi {dockerhubUsername/imageName:tag}"
}
}
stage ("docker clear") {
sshagent(credentials: ['server-access-key']) {
sh '''
ssh -o StrictHostKeyChecking=no ubuntu@{스프링부트 서버 IP주소} uptime
ssh -t ubuntu@{스프링부트 서버 IP주소} echo $DOCKER_HUB_PASSWORD | docker login -u $DOCKER_HUB_USERNAME --password-stdin
ssh -t ubuntu@{스프링부트 서버 IP주소} chmod +x ./deploy.sh
ssh -t ubuntu@{스프링부트 서버 IP주소} ./deploy.sh
'''
}
}
}
}
중간의 DOCKER_HUB_~
는 내가 설정한 환경변수이다.
Jenkins관리 -> System 이동 후 중간쯤 Global properties에서 설정해 주면 된다.
deploy.sh
!#/bin/bash
docker pull iwasacar/iwasacar-server
docker run -d --name iwasacar-server -p 80:8080 iwasacar/iwasacar-server
docker hub에 push 된 image를 pull 받아 실행해 주면 된다.
사실 현재는 repository가 public이라 쉽게 배포했지만, private 환경에서 ssh를 통해 clone을 받으려니 잘 되지 않았다. 꼭 해결하고 싶은 이슈이다.
그리고 운영서버와 개발서버를 나눠 운영할 때도 branch를 어떻게 관리할지 고민해 봐야겠다.
Vue.js Jenkins 파이프라인 생성
pipeline {
agent any
tools {nodejs 'Node18'}
stages {
stage('git clone') {
steps {
git branch: 'main',
url: '${github repository url.git}'
}
}
stage('build'){
steps {
sh '''
npm install
npm run build
'''
}
}
stage('deploy'){
steps{
sshagent(credentials:['vue server access key']){
sh '''
tar -cf dist.tar dist
ssh -o StrictHostKeyChecking=no ubuntu@{vue server ip} uptime
scp dist.tar ubuntu@{vue server ip}:/home/ubuntu
ssh -t ubuntu@{vue server ip} chmod +x ./deploy.sh
ssh -t ubuntu@{vue server ip} ./deploy.sh
'''
}
}
}
}
}
Vue js 어플리케이션을 스프링과 다르게 정적 파일을 Nginx를 통해 서빙하기 때문에 빌드된 정적 파일을 압축해서 EC2 서버에 배포한다.
위 과정에서 두 가지 플러그인을 설치해야한다.
위 두가지 플러그인을 받도록 하자.
그 후 두 가지 설정이 필요하다
1. 노드 설정
2. ssh를 위한 private키 설정
vue server에 접근할 때 사용하는 pem키를 넣어주자
deploy.sh
#!/bin/bash
tar -xf dist.tar
sudo rm -r /var/www/html/dist
sudo mv ./dist /var/www/html
Nginx가 실행되는 프론트 서버에 위 스크립트를 적절한 경로에 저장하자.
정리
위와 같이 프론트엔드와 백엔드 CI/CD 파이프라인을 만들어봤다.
그렇지만 아직 SSH로 Clone, branch 관리, 무중단 배포 등 해결할 문제가 조금 남았다.
배포를 완벽하게 하고 개발도 어느정도 궤도에 오르면 이슈를 하나씩 해결해야겠다.
'우리 FISA' 카테고리의 다른 글
우리FISA 클라우드 서비스 개발 - Spring Boot 어플리케이션에서 RDS MySQL 이중화 (1) | 2023.08.29 |
---|---|
우리FISA 클라우드 서비스 개발 - 프로젝트 시작과 프로젝트 산출물 (0) | 2023.08.13 |
우리FISA 클라우드 서비스 개발 - Spring Framework에서 테스트 (0) | 2023.08.06 |
우리FISA 클라우드 서비스 개발 - EC2, Docker, Jenkins를 사용한 Spring-boot 어플리케이션 배포 (0) | 2023.07.30 |
댓글