
pipeline {
agent any
tools {nodejs "nodejs"}
environment {
imageName = "이미지이름 넣기"
registryCredential = 'dockerhub' //젠킨스에 등록해놓은 자격증명서
dockerImage = ''
releaseServerAccount = 'ubuntu'
releaseServerUri = '서비스 URL EC2서버'
releasePort = '리액트가 사용하는 포트'
}
stages {
stage('Git Clone') {
steps {
git branch: 'FE',
credentialsId: 'gitlab', //젠킨스에 등록해놓은 자격증명서
url: 'URL.git' //git clone할 때 사용하는 url
}
}
stage('Image Build & DockerHub Push') {
steps {
dir('frontend') {
script {
docker.withRegistry('', registryCredential) {
sh "docker buildx create --use --name mybuilder"
sh "docker buildx build --platform linux/amd64,linux/arm64 -t $imageName:latest --push ."
}
}
}
}
}
stage('Before Service Stop') {
steps {
sshagent(credentials: ['ubuntu-c106']) {
sh '''
if test "`ssh -o StrictHostKeyChecking=no $releaseServerAccount@$releaseServerUri "docker ps -aq --filter ancestor=mooncheolhwan/frontend:latest"`"; then
ssh -o StrictHostKeyChecking=no $releaseServerAccount@$releaseServerUri "docker stop $(docker ps -aq --filter ancestor=mooncheolhwan/frontend:latest)"
ssh -o StrictHostKeyChecking=no $releaseServerAccount@$releaseServerUri "docker rm -f $(docker ps -aq --filter ancestor=mooncheolhwan/frontend:latest)"
ssh -o StrictHostKeyChecking=no $releaseServerAccount@$releaseServerUri "docker rmi mooncheolhwan/frontend:latest"
fi
'''
}
}
}
stage('DockerHub Pull') {
steps {
sshagent(credentials: ['ubuntu-c106']) {
sh "ssh -o StrictHostKeyChecking=no $releaseServerAccount@$releaseServerUri 'sudo docker pull $imageName:latest'"
}
}
}
stage('Service Start') {
steps {
sshagent(credentials: ['ubuntu-c106']) {
sh '''
ssh -o StrictHostKeyChecking=no $releaseServerAccount@$releaseServerUri "sudo docker rm -f fe"
ssh -o StrictHostKeyChecking=no $releaseServerAccount@$releaseServerUri "sudo docker run -i -e TZ=Asia/Seoul --name fe -p $releasePort:$releasePort -d $imageName:latest"
'''
}
}
}
stage('Service Check') {
steps {
sshagent(credentials: ['ubuntu-c106']) {
sh '''
#!/bin/bash
for retry_count in \$(seq 20)
do
if curl -s "URL" > /dev/null
then
curl -d '{"text":"Release Complete"}' -H "Content-Type: application/json" -X POST 메타모스트 웹훅
break
fi
if [ $retry_count -eq 20 ]
then
curl -d '{"text":"Release Fail"}' -H "Content-Type: application/json" -X POST 메타모스트 웹훅
exit 1
fi
echo "The server is not alive yet. Retry health check in 5 seconds..."
sleep 5
done
'''
}
}
}
}
}
위 코드로 진행되었습니다.
단계는 6단계로,
1. Git Clone : Git 저장소에서 소스 코드를 가져옵니다.
2. Image Build & DockerHub Push : Docker 이미지를 빌드하고 DockerHub에 푸시합니다.
3. Before Service Stop : 이전에 실행된 Docker 컨테이너를 중지하고 제거합니다.
4. DockerHub Pull : 새로 업데이트된 Docker이미지를 서버로 가져옵니다.
5. Service Start : 새로운 Docker컨테이너를 시작합니다.
6. Service Check : 서비스가 올바르게 시작되었는지 확인합니다.
agent any : 어떤 에이전트에서든 실행될 수 있다.
tools : 파이프라인에서 사용하는 도구
environment : 환경 변수 정의함.
stages : 파이프라인의 주요 단계 정의
steps : 각 단계에서 실행할 명령, shell 스크립트로 실행됨.
--use : 새로 생성된 빌더를 사용하도록 설정합니다.--name mybuilder : 새로 생성된 빌더의 이름을 "mybuilder"로 지정합니다.--platform linux/amd64,linux/arm64 : 빌드할 이미지의 플랫폼을 지정합니다. 여기서는 Linux의 amd64 아키텍처와 arm64 아키텍처를 지정했습니다. 즉, 이 명령은 amd64와 arm64 아키텍처용 이미지를 동시에 빌드합니다.-t $imageName:latest : 빌드한 이미지에 태그를 지정합니다. $imageName은 환경 변수로 설정된 이미지 이름을 나타냅니다. latest는 태그로서, 이 이미지가 최신 버전임을 나타냅니다.--push : 빌드된 이미지를 레지스트리에 푸시합니다.. : 현재 디렉토리에서 Dockerfile을 사용하여 이미지를 빌드합니다.docker stop 명령을 사용하여 원격 서버에서 실행 중인 특정 이미지를 기반으로한 컨테이너를 중지합니다.docker rm -f 명령을 사용하여 원격 서버에서 실행 중인 특정 이미지를 기반으로한 컨테이너를 강제로 제거합니다.docker rmi 명령을 사용하여 해당 이미지를 원격 서버에서 제거합니다.sudo docker rm -f fe 명령을 실행합니다.-f 옵션은 강제로 컨테이너를 제거-i : 인터랙티브 모드로 실행합니다.-e TZ=Asia/Seoul : 컨테이너 내부의 시간대를 Asia/Seoul로 설정합니다.--name fe : 컨테이너의 이름을 fe로 지정합니다.-p $releasePort:$releasePort : 호스트의 $releasePort 포트를 컨테이너의 동일한 포트로 매핑합니다.-d : 백그라운드 모드로 실행합니다.$imageName:latest: 실행할 이미지의 이름과 태그를 지정합니다. $imageName은 환경 변수로 설정된 이미지 이름을 나타냅니다.마지막 step인 Service Check 코드에 대해 설명하자면,
for retry_count in \$(seq 20): 20번의 반복을 수행하는 for 루프를 시작합니다.if curl -s "URL" > /dev/null: curl을 사용하여 특정 URL로 HTTP GET 요청을 보냅니다. -s 옵션은 silent 모드로 출력을 표시하지 않습니다. 응답은 /dev/null로 보냅니다.curl -d '{"text":"Release Complete"}' -H "Content-Type: application/json" -X POST 메타모스트 웹훅: Release Complete 메시지를 포함한 JSON 데이터를 지정된 웹훅 URL로 POST 요청을 보냅니다.if [ $retry_count -eq 20 ]: 20번의 시도가 모두 실패한 경우 실행합니다.curl -d '{"text":"Release Fail"}' -H "Content-Type: application/json" -X POST 메타모스트 웹훅 : Release Fail 메시지를 포함한 JSON 데이터를 지정된 웹훅 URL로 POST 요청을 보냅니다.echo "The server is not alive yet. Retry health check in 5 seconds...": 서버가 아직 준비되지 않았음을 나타내는 메시지를 출력합니다.