본문 바로가기
한화시스템 Beyond SW Camp/데브옵스

[Jenkins] Jenkins 설치, GitHub 웹훅을 사용한 자동 배포

by taeh00n 2025. 3. 19.

Jenkins란?

CI/CD(지속적 통합 및 지속적 배포)

 

CI (지속적 통합, Continuous Integration) : Jenkins는 개발자들이 작성한 코드를 자주 통합하고 그 통합된 코드가 자동으로 빌드되고 테스트되도록 도와준다. 이를 통해 개발자들이 코드 변경 사항을 빠르게 통합하여 버그를 조기에 발견하고, 품질을 개선할 수 있다.

 

CD (지속적 배포, Continuous Delivery 또는 Continuous Deployment) : Jenkins는 빌드된 애플리케이션을 자동으로 테스트하고 배포 환경에 배포하는 작업을 자동화한다. 이는 자동화된 파이프라인을 통해 빠르고 안전하게 배포가 이루어지게 도와준다.


Jenkins 설치

레포지토리 추가

curl -fsSL https://pkg.jenkins.io/debian/jenkins.io-2023.key | sudo tee /usr/share/keyrings/jenkins-keyring.asc > /dev/null
echo deb [signed-by=/usr/share/keyrings/jenkins-keyring.asc] https://pkg.jenkins.io/debian binary/ | sudo tee /etc/apt/sources.list.d/jenkins.list > /dev/null

apt update

자바 설치

apt install openjdk-17-jdk

젠킨스 설치 및  실행

apt install jenkins
systemctl restart jenkins

대시보드 접속

cat /var/lib/jenkins/secrets/initialAdminPassword

여기서 패스워드 확인을 해서 대시보드에 입력을 한다.

 

이후에 계정 생성을 하고 기본값으로 실행을 하면된다.

Jenkins 설치 완료


Github Webhook을 이용한 자동배포

레포지토리 생성 후 Github Webhook 생성

파이프라인 생성

GitHub hook trigger for GITScm pollin이 설정되어 있다면, 별도의 웹훅 엔드포인트(/github-webhook/)를 설정하지 않아도 Jenkins가 GitHub에서 변경 사항을 감지하고 빌드를 트리거한다.

위 모든 과정을 해도 Webhook이 오류 표시가 떠있으면 Redeliver 눌러보기

Jenkins에서 배포 서버 패스워드 없이 접속하게 설정하기

Jenkins 서버에서 아래의 명령어 입력

sudo su - jenkins
ssh-keygen

ssh-keygen 명령어를 실행하면 3개의 입력을 해야한다.

1번째 : 파일 저장 경로 설정

그냥 엔터를 치면 기본값인 ~/.ssh/id_rsa로 키 생성

2번째 : 패스프레이즈 설정 (암호화 비밀번호)  

아무것도 입력하지 않고 엔터 → 패스프레이즈 없이 생성 (SSH 사용 시 비밀번호 없이 사용가능)

3번째 : 패스프레이즈 확인

패스프레이즈를 설정하지 않았기 때문에 다시 엔터

 

즉 ssh-keygen 명령어 실행 후 엔터 3번을 치면된다.

ssh-copy-id   test@배포서버IP

배포서버의 패스워드를 입력한다.

ssh test@배포서버IP

설정이 정상적으로 되었다면 위의 명령어를 실행 시 비밀번호 없이 배포 서버에 접속이 가능할 것이다. 


Execute Shell 설정

아래의 Shell들은 GitHub 푸시 이벤트가 감지되었을 때 실행되는 Jenkins 파이프라인에 포함된다.

주의

Execute Shell 설정에서 Docker에 푸시하는 과정이 포함되어있을 떄 아이디와 패스워드를 작성하는 경우가 있는데 이때 소셜 로그인으로 Docker에 가입했을 경우 연결이 되지 않는다.

위의 과정을 통해 이메일에서 Password Reset을 진행한 후 정상적으로 연결할 수 있게 된다

예시1

Gradle 빌드 후 JAR 파일을 서버로 복사하고 기존 프로세스를 종료한 후 새 애플리케이션을 실행하는 스크립트.

echo "Add Permission"
chmod +x /var/lib/jenkins/workspace/webhook_test/demo/gradlew

echo "Gradle Build"
cd /var/lib/jenkins/workspace/webhook_test/demo  
./gradlew bootJar

echo "Copy jar File"
scp /var/lib/jenkins/workspace/webhook_test/demo/build/libs/demo-0.0.1-SNAPSHOT.jar  test@10.10.10.90:/home/test/app.jar

ssh test@10.10.10.90 << 'EOF'
  echo "Find and Kill Running Process"
  PID=$(pgrep -f "java -jar /home/test/app.jar")
  if [ ! -z "$PID" ]; then
    echo "Stopping process $PID"
    kill -15 $PID
    sleep 5  # 종료 대기
    if ps -p $PID > /dev/null; then
      echo "Force killing process $PID"
      kill -9 $PID
    fi
  else
    echo "No running process found."
  fi
EOF

echo "Restart Application"
ssh test@10.10.10.90 nohup java -jar /home/test/app.jar &

sleep 3

 

예시2

Gradle 빌드 후 Docker 이미지를 생성하고, Docker Hub에 이미지를 푸시하는 스크립트.

echo "Add Permission"
chmod +x /var/lib/jenkins/workspace/webhook_test/demo/gradlew

echo "Gradle Build"
cd /var/lib/jenkins/workspace/webhook_test/demo  
./gradlew bootJar

echo "Docker Build"
docker build --tag xogns0518/jenkins_test:$BUILD_ID  /var/lib/jenkins/workspace/webhook_test/

echo "Docker Login"
docker login -u [Docker아이디] -p [Docker비밀번호]

echo "Docker Push"
docker push xogns0518/jenkins_test:$BUILD_ID

 

예시3

Gradle 빌드 후 Docker 이미지를 생성하고, Docker Hub에 이미지를 푸시한 후 Kubernetes에 배포하는 스크립트

echo "Add Permission"
chmod +x /var/lib/jenkins/workspace/webhook_test/demo/gradlew

echo "Gradle Build"
cd /var/lib/jenkins/workspace/webhook_test/demo  
./gradlew bootJar

echo "Docker Build"
docker build --tag xogns0518/jenkins_test:$BUILD_ID  /var/lib/jenkins/workspace/webhook_test/demo

echo "Docker Login"
docker login -u [Docker아이디] -p [Docker비밀번호]

echo "Docker Push"
docker push xogns0518/jenkins_test:$BUILD_ID

echo "Deployment"
ssh test@192.0.3.10 kubectl apply -f - <<EOF
apiVersion: apps/v1
kind: Deployment
metadata:
  name: backend
  namespace: cth
spec:
  selector:
    matchLabels:
      type: backend
  replicas: 1
  template:
    metadata:
      labels:
        type: backend
    spec:
      containers:
      - name: backend
        image: xogns0518/jenkins_test:$BUILD_ID
EOF

Kubernetes 서버에도 비밀번호 없이 접속하기 위해서는 위에서 한 비밀번호 없이 접속 설정을 Kubernetes 서버 대상으로 해줘야 한다.

 

위의 Shell들을 입력할 때 서버에서의 프로젝트 파일 위치, Gradle 파일 위치배포 서버의 IP주소를 꼭 확인해주자