Docker-compose를 이용한 Spring(+Redis +MySQL), Jenkins 배포(1)에서는 docker-compose로 Spring, Redis, MySQL을 컨테이너로 띄워 외부와도 연동됨을 확인하였다. 본 게시글에서는 docker-compose.yml에서 마저 설명하지 못했던 jenkins에 대하여 연동과정, jenkins 환경설정등에 대하여 설명한다.
Jenkins란?
Jenkins는 *지속적인 통합/배포(CI,CD)을 가능하게 하는 Java로 작성된 오픈 소스 자동화 도구이며, 다양한 언어로 작성된 프로젝트에 지원이 가능하다. Jenkins를 통해 개발자는 프로젝트에 변경 사항을 더 쉽게 통합하고 새로운 빌드를 더 쉽게 얻을 수 있다. 또한 많은 테스트 및 배포 기술과 통합하여 소프트웨어를 지속적으로 제공할 수 있다.
*지속적인 통합/배포(CI,CD) : 지속적인 통합 (Continuous Integration, CI)은 개발자들이 코드를 작성하고 변경사항을 공유 저장소에 자주 업로드하는 개발 방법이다. 즉, 개발을 하면서 코드에 대한 통합을 지속적으로 진행하면서 품질을 유지하기 위한 방법이다. Jenkins는 코드 변경 사항을 자동으로 감지하고, 이를 빌드 및 테스트하는 작업을 수행한다.
지속적인 배포 (Continuous Deployment, CD)는 소프트웨어 개발 및 배포 프로세스의 자동화를 의미한다. CD는 지속적인 통합 (Continuous Integration, CI)의 확장으로 볼 수 있다. CI가 개발자가 코드 변경을 주기적으로 통합하고 빌드 및 테스트하는 것을 강조한다면, CD는 이러한 빌드 및 테스트 결과를 자동으로 프로덕션 환경으로 배포하여 실제 사용자에게 즉시 제공하는 것을 목표로 한다.
docker-compose로 Jenkins 배포
...
jenkins:
image: jenkins/jenkins:lts
container_name: jenkins
ports:
- "8080:8080"
volumes:
- jenkins_home:/var/jenkins_home
network_mode: host
volumes:
jenkins_home:
"Docker-compose를 이용한 Spring(+Redis +MySQL), Jenkins 배포(1)"에서는 docker-compose.yml에서 Jenkins에 대한 서비스를 따로 부연설명하지 않았기 때문에 본 게시글에서 따로 설명을 하려한다.
`volumes` 섹션은 컨테이너와 호스트 간의 볼륨 매핑을 설정하는 곳이다. 볼륨 매핑을 통해 컨테이너 내부의 파일이 호스트의 파일 시스템과 공유된다.
여기서 `jenkins_home`은 볼륨의 이름이다. 볼륨 이름은 임의로 정의할 수 있으며, 컨테이너 내부에서 이 이름을 사용하여 해당 볼륨을 참조할 수 있다.
`jenkins_home:/var/jenkins_home`은 볼륨 매핑의 구성을 나타낸다. `jenkins_home`은 호스트의 디렉토리 또는 볼륨을 의미하며, `/var/jenkins_home`은 컨테이너 내부의 경로를 나타낸다. 이 구성은 호스트의 `jenkins_home` 디렉토리와 컨테이너의 `/var/jenkins_home` 디렉토리를 매핑한다. 즉, 호스트의 `jenkins_home` 디렉토리의 내용과 컨테이너의 `/var/jenkins_home` 디렉토리의 내용이 공유된다.
`network_mode: host`는 컨테이너가 호스트의 네트워크 인터페이스를 직접 사용하도록 설정하는 옵션이다. 일반적으로 Docker 컨테이너는 가상 네트워크를 생성하여 컨테이너 간 통신을 관리한다. 그러나 `network_mode: host`를 설정하면 컨테이너가 호스트의 네트워크 인터페이스를 공유하므로 컨테이너 내부의 서비스는 호스트와 동일한 네트워크에 직접 접근할 수 있다.
Jenkins 컨테이너 SSH 생성
"docker-compose up --build -d"를 통해 Jenkins가 컨테이너로 띄워짐을 확인하였다면 다음은 Jenkins에 접속해야한다.
젠킨스 접속
docker exec -it jenkins bash
젠킨스 public key 생성
ssh-keygen -t rsa
public key 확인
cat /var/jenkins_home/.ssh/id_rsa.pub
이후 나오는 ssh~의 구문을 복사하여 갖고있는다.
인스턴스의 root로 이동한 다음 "vim ~/.ssh/authorized_keys"를 입력하여 파일에 접속한 뒤 복사한 ssh를 붙여넣기한다.
vim ~/.ssh/authorized_keys
initialAdminPassword 확인
docker logs [jenkins 컨테이너 이름]
jenkins/jenkins:lts 이미지는 비밀번호를 로그로 남기게 되어이씩 때문에 화면에 비밀번호가 출력된다. 이를 복사하여 갖고있는다.
Jenkins 환경설정
위의 과정을 완료하였다면 "인스턴스의 Public IP:8080"으로 외부에서 젠킨스에 접속한다. 이 때 인스턴스의 보안 인바운드 규칙은 8080에 대해 열려있어야 한다!!
password에는 위에서 복사한 jenkins 컨테이너 비밀번호를 붙여넣기 한 뒤 Jenkins 접속한다.
Customize Jenkins에서 Install suggested plugins 선택
젠킨스가 시작하고 있음을 확인하는 화면이다.
본인의 계정을 생성하면
이제 Jenkins에서 Item을 만들어서 CI/CD를 구현할 것이다.
새로운 Item 클릭 - Item 이름 입력 - Freestyle project 클릭
소스 코드 관리에서 본인 프로젝트가 위치한 github의 URL을 입력한 후 Credentials Add를 클릭한다.
kind: SSH Username with private key
Username: github 아이디
Password: github 비밀번호
빌드 유발에서는 GitHub hook trigger for GITScm polling을 체크한다.
Build Steps를 작성한다.
Command는 다음과 같은데 이를 하나하나 설명해보자면
chmod +x ./gradlew
./gradlew build -x test
ssh -t -t ubuntu@master$(/sbin/ip route | awk '/default/ { print $3 }') <<EOF
cd Back-end
docker-compose up --build -d
exit
EOF
1. "chmod +x ./gradlew
./gradlew build -x test"
해당 명령어는 젠킨스가 돌아가고 있는 인스턴스에서 스프링 프로젝트를 자동으로 build 해주는 명령어이다.
2."ssh -t -t ubuntu@master$(/sbin/ip route | awk '/default/ { print $3 }') <<EOF
cd Back-end
docker-compose up --build -d
exit
EOF"
다음의 명령어는 도커 컨테이너에서 나의 aws 인스턴스에 접속한 뒤 Back-end의 디렉토리에서 docker-compose를 실행시켜 컨테이너를 띄우는 명령어이다.
이전에서 변동된 git 소스코드가 build 되었으므로 Dockerfile또한 다시 실행되어야 한다. 그 때문에 docker-compose.yml을 실행시키기 위해서 위의 명령어를 Build steps에 입력한다.
*여기서 "ubuntu@master" 부분은 사용자마다 다를 수도 있으니 본인이 맨 처음 aws 인스턴스에 접속했을 때 $ 전까지의 문장을 복사해서 사용해야 할 것이다.
Git 프로젝트의 Webhook을 Jenkins와 연동하고 나면(추후 설명한다.) 프로젝트에서 Git push를 할 때마다 Jenkins가 다음과 같이 Build되며 Build Steps의 구문을 Jenkins 컨테이너가 띄워지고 있는 인스턴스에서 실행시킨다.
Build steps를 작성한 후 BestRestaurant라는 Item이 생성된 모습이다.
Jenins, Git Webhook
본인의 git project의 repository로 가서 settings를 클릭한다.
Webhooks를 클릭 - Add Webhook을 클릭 - payload URL에 http://[ec2-주소]:[포트포워딩한 포트]/github-webhook/입력
위의 모든 설정을 마친 뒤 스프링 프로젝트에서 git push를 진행하면 젠킨스에서 build가 되며 Build steps의 명령어가 실행되고 자동으로 배포가 됨을 확인할 수 있다.
대학교 기말 팀 프로젝트를 진행하며 생소한 클라우드 개념을 배우고, 이를 직접 사용해보았는데 무척이나 귀중한 경험이었다고 생각한다. 해당 프로젝트를 진행하며 본 게시글에서 전부 설명하지 못할정도의 많은 개념을 배웠으며, 에러 또한 끊이지 않아 계속 고생하였다. 다만 프로젝트를 완성시킨 후 되돌아보니 새로 배운 개념을 적용하거나 에러를 잡는 과정 피와 살이되는 경험이라 생각하고 있다.
또한 본 게시글은 다음의 블로그에서 많은 도움을 받아 작성하였다.
[Jenkins] Docker를 활용한 Spring boot 프로젝트 CI & CD (tistory.com)
'개발 > Cloud' 카테고리의 다른 글
Docker-compose를 이용한 Spring(+Redis +MySQL), Jenkins 배포(1) (0) | 2023.06.25 |
---|