목표 : 현재 하고 있는 프로젝트의 깃허브 변경사항이 있을때 소스를 빌드해서 배포서버에 전달하는 것
추가 목표 : 빌드 시간이 너무 많이 걸려서 어느부분이 많이 걸리는지 구분해서 분석
- 도커 설치.
- 리눅스 설치 링크 : https://docs.docker.com/desktop/install/linux-install/
- 윈도우 설치 링크 : https://docs.docker.com/desktop/install/windows-install/
- 실리콘 맥에서 설치 권장하지 않음.
- 젠킨스 설치.
- 도커 이미지 lts-jdk11 선택 ( jenkins/jenkins:lts-jdk11 )
- 환경변수
- docker run -d --name my-jenkins
- -p 50000 : 50000
- -p 8080 : 8080 - 실질적으로 사용하는 포트
- -v /jenkins/data : /var/jenkins_home - 데이터 폴더 마운트
- -e TZ=Asia/Seoul
- (개인 옵션)-v /var/run/docker.sock:/var/run/docker.sock
- (개인 옵션) --link my-sonarqube
- jenkins/jenkins:lts-jdk11
- (옵션) 추가 설정해줘야 할것
- DNS/SSL 설정(외부 접속) - 리버스 프록시 활용
- Docker run 명령어
- 젠킨스 초기 설정
- 초기 비밀번호 - 로그값에서 복사하여 붙여 넣고 초기로그인
- 사용자 설정 - 앞으로 로그인하게될 계정
- ssh-keygen 명령어를 사용, pub키, private 키 생성
- Jenkins 관리 -> Manage Credentials -> Domains -> global
- kind - SSH Username with private key
- Username = 키 사용시 식별값(ex = jenkins_ssh_key)
- Private Key = private 키 값 입력
- 젠킨스 플러그인 설치
- SSH Agent Plugin
- Gradle Plugin
- Nodejs Plugin
- 젠킨스 플러그인 환경 설정
- 젠킨스 관리 -> Global Tool Configuration
- Add 사용하는 플러그인(Gradle, Nodejs)
- 식별값 설정 ex("프로젝트 이름")
- 버전 설정, Install automatically 체크
- (옵션) 도커 외부 환경 path도 등록 가능함
- 젠킨스 Item 유형 선택(프리스타일, 파이프라인).
- Dashboard -> +새로운 Item
- Enter an item name -> my-app
- Github, 원격서버에 pub키 추가
- Github settings -> SSH ans GPG keys -> New SSH key
- title = jenkins
- key = 상단에서 생성한 pub키(id_rsa.pub) 입력
- 오류 대응
- code 128 오류시 "git.exe ls-remote -h -- git@github.com:깃네임/리파지토리.git HEAD" 입력후 fingerprint 등록
- 원격 서버 접속(ssh 유저이름@주소)
- cd .ssh (폴더이동)
- vi authorized_keys (젠킨슨 접속용 키값 입력)
- 상단에서 생성한 pub키(id_rsa.pub) 복사후 입력
- 오류대응
- code 128 오류시 "ssh 원격유저네임@원격서버"
- finger print 재등록을 원하면 "ssh-keygen -r 원격서버" 후 다시 시도
- Github settings -> SSH ans GPG keys -> New SSH key
- 파이프라인 설정.
- (옵션) 이 빌드는 매개변수가 있습니다.
- (옵션) Github hook trigger for GISTcm polling
- 깃헙->프로젝트->Settings->WebHooks
- Add webhook = 젠킨스(DNS) 주소/github-webhook/ 등록
- 초록 체크 표시 확인
- 수동으로 빌드 1번 실행해야 이후 자동화 됨.
- Pipe line script from SCM
- SCM -> Git 선택
- 깃허브 리파지토리에 Jenkinsfile을 생성한다.
- Jenkinsfile 내용( 하단 첨부 - 내용 확인후 수정필)
- 파이프 라인 실행 순서
- 젠킨슨이 깃허브 리파지토리의 접속
- 등록된 credential 값(private key)을 사용
- Jenkinsfile 을 읽어 들여서 준비 단계 진입
- 등록해둔 plugin 들을 사용해서 소스 빌드 & 처리
- 원격 서버에 접속
- 등록된 credential 값(private key)을 사용
- 원격 서버에 빌드 파일 업로드&배포 스크립트 실행
- 젠킨스 저서버의 환경 고려값
- core 보다는 ram용량이 중요
- 리눅스 스왑 메모리 조정하여 메모리 총합 2~3기가 적당
- 설정의 of executors 값을 1개로 조정해서 순차적으로 빌드 실행
- ssd 사용, ram 용량 증설
- 젠킨스 에이전트를 추가 (ios,mfc 등등 다른 환경에서도 활용 가능)
- core 보다는 ram용량이 중요
7.3.3 Jenkins 파일 내용 - 수정(2022.11.20)
pipeline {
agent any
tools{
//프론트 빌드를 위한 nodejs
nodejs "프로젝트명"
//백엔드 빌드를 위한 gradle
gradle "프로젝트명"
}
environment {
SSH_CREDENTIAL_ID= '생성했던 Credential ID 값'
GIT_URL= 'git@github.com:깃네임/리파지토리.git'
REMOTE_HOST='원격서버'
REMOTE_USER='원격서버유저이름'
}
stages {
stage('Prepare') {
steps {
echo '준비 단계'
git branch: 'main',
credentialsId: "${SSH_CREDENTIAL_ID}",
url: "${GIT_URL}"
echo '01. OAuth_Client&Url'
// 백엔드 설정값 (이 빌드에는 매개변수가 있습니다. 에서 입력한 값으로 파일 변경)
sh' sed -i "s/{KAKAO_CLIENT_ID}/${KAKAO_CLIENT_ID}/" "${WORKSPACE}/backend/src/main/resources/application.yml"'
sh' sed -i "s/{KAKAO_CLIENT_SECRET}/${KAKAO_CLIENT_SECRET}/" "${WORKSPACE}/backend/src/main/resources/application.yml"'
sh' sed -i "s/{FRONT_URL}/${FRONT_URL}/" "${WORKSPACE}/backend/src/main/resources/application.yml"'
sh' sed -i "s/{FRONT_URL_REDIRECT}/${FRONT_URL_REDIRECT}/" "${WORKSPACE}/backend/src/main/resources/application.yml"'
echo '02. JWT_TOKEN'
sh 'sed -i "s/{JWT_SECRET}/${JWT_SECRET}/" "${WORKSPACE}/backend/src/main/resources/application.yml"'
sh 'sed -i "s/{TOKEN_SECRET}/${TOKEN_SECRET}/" "${WORKSPACE}/backend/src/main/resources/application.yml"'
}
post {
success {
sh 'echo "Successfully Cloned Repository"'
}
failure {
sh 'echo "Fail Cloned Repository"'
}
}
}
stage('Front Build') {
steps {
echo '프론트 빌드 단계'
dir('./web'){
sh 'pwd'
sh 'npm install'
sh 'CI=false npm run build'
}
dir('.'){
sh 'cp -r web/dist nginx/build'
}
}
post {
success {
echo 'Front Build build success'
}
failure {
echo 'Front Build build failed'
}
}
}
stage('Backend Build') {
steps {
echo '백엔드 빌드 단계'
// 내부 폴더 이동 = 명령어 cd
dir('./backend'){
sh './gradlew clean'
sh './gradlew build -x check'
}
}
post {
success {
echo 'Backend Build success'
}
failure {
echo 'Backend Build failed'
}
}
}
stage('Front Test'){
steps {
echo '프론트 테스트 단계'
}
post {
success {
echo 'Front Test success'
}
failure {
echo 'Front Test failed'
}
}
}
stage('Backend Test'){
steps {
echo '백엔드 테스트 단계'
// 내부 폴더 이동 = 명령어 cd
dir('./backend'){
sh './gradlew test'
}
}
post {
success {
echo 'Backend Test success'
}
failure {
echo 'Backend Test failed'
}
}
}
stage('Backend File Transfer'){
steps{
echo '백엔드 파일 전송 단계'
script {
dir('./backend'){
// 상단에서 설치한 sshagent
sshagent (credentials: ["${SSH_CREDENTIAL_ID}"]){
sh """
scp -r build/libs ${REMOTE_USER}@${REMOTE_HOST}:프로젝트명/backend
"""
}
}
}
}
post{
success{
echo 'File Transfer success'
}
failure{
echo 'File Transfer failed'
}
}
}
stage('Front File Transfer'){
steps{
echo '프론트 파일 전송 단계'
script {
dir('./web'){
//빌드 폴더 정리
sh 'rm -rf build'
sh 'mv dist build'
// 상단에서 설치한 sshagent
sshagent (credentials: ["${SSH_CREDENTIAL_ID}"]){
sh """
ssh ${REMOTE_USER}@${REMOTE_HOST} "rm -rf 프로젝트명/nginx/build"
scp -r build ${REMOTE_USER}@${REMOTE_HOST}:프로젝트명/nginx/
"""
}
}
}
}
post{
success{
echo 'Front File Transfer success'
}
failure{
echo 'Front File Transfer failed'
}
}
}
stage('Gateway File Transfer'){
steps{
echo '게이트웨이 파일 전송 단계'
script {
dir('./nginx'){
sshagent (credentials: ["${SSH_CREDENTIAL_ID}"]){
sh """
scp nginx.conf ${REMOTE_USER}@${REMOTE_HOST}:프로젝트/nginx/
scp Dockerfile ${REMOTE_USER}@${REMOTE_HOST}:프로젝트/nginx/
"""
}
}
}
}
post{
success{
echo 'Gateway File Transfer success'
}
failure{
echo 'Gateway File Transfer failed'
}
}
}
stage('Remote Docker build'){
steps{
echo '원격 도커 빌드 단계'
sshagent (credentials: ["${SSH_CREDENTIAL_ID}"]){
sh """
ssh ${REMOTE_USER}@${REMOTE_HOST} "cd /home/ubuntu/프로젝트명 && docker compose down && docker compose build --no-cache"
"""
}
}
post{
success{
echo 'deploy success'
}
failure{
echo 'deploy failed'
}
}
}
stage('Remote Docker Deploy'){
steps{
echo '배포 단계'
sshagent (credentials: ["${SSH_CREDENTIAL_ID}"]){
sh """
ssh ${REMOTE_USER}@${REMOTE_HOST} "cd /home/ubuntu/프로젝트명 && docker compose up -d"
"""
}
}
post{
success{
echo 'deploy success'
}
failure{
echo 'deploy failed'
}
}
}
}
}
참고 링크 :
- https://lovethefeel.tistory.com/m/94
- https://hudi.blog/continuous-deploy-with-jenkins-1-backend/
- https://royleej9.tistory.com/m/entry/Jenkins-SSH-%EC%82%AC%EC%9A%A9-pipeline-SSH-Agent
- https://velog.io/@mooh2jj/jenkins-docker-gradle-%EC%9E%90%EB%8F%99%EB%B0%B0%ED%8F%AC
- 그외
'교육 > devops' 카테고리의 다른 글
[SONARQUBE&JENKINS] 소나 큐브, 젠킨스 파이프라인 적용 (0) | 2022.11.26 |
---|---|
[SONARQUBE] 소나큐브 셋팅 (0) | 2022.11.26 |