본문 바로가기

Jenkins

[Jenkins] Jenkins란? Jenkins를 사용하는 이유 및 Declarative pipeline 문법

Jenkins

Jenkins는 소프트웨어 구축, 테스트, 전달 및 배포와 관련된 모든 종류의 작업을 자동화하는데 사용할 수 있는 오픈 소스 자동화 서버이다.

 

Jenkins는 시스템 패키지, Docker 또는 JRE(Java Runtime Environment)가 설치된 모든 환경에서 실행할 수 있다. 

이러한 자동화 시스템은 다양한 플러그인들을 조합하여 일을 처리하는 Pipeline을 통해 CI/CD Pipeline을 구축할 수 있다.

 

개발자들이 코드 작성 외에 귀찮은 테스트, 빌드, 배포 등의 과정을 Jenkins에 구축해놓으면 대신 이 일들을 처리해 준다. (자동화)

 

쉽게 말해 그림에서 보이는것과 같이 노예이다.

 

대표적인 Plugin

대표적인 Plgin으로는 PipelineGradle PluginGit plugin 등이 있는데 Jenkins 처음 설치 시 추천 Plugin을 설치하면(시작 과정 있음) 웬만한건 다 설치 된다.

 

Pipeline

Pipeline이란 CI/CD 를 구현하고 지원하기위한 플러그인들의 모음이다. 여러 플러그인들 중 자신의 시스템에 맞게 사용하도록 정의하여 만들어진 Pipeline을 통해 서비스가 배포된다.

 

Pipeline은 Pipeline DSL 코드로 작업 순서를 작성할 수 있다.  

Pipeline DSL 에는  DeclarativeScripted Pipeline 두 가지가 존재한다.

 

공식 문서에서는 Declarative Pipeline이 최신 기능으로 Scripted Pipeline 구문보다 더 많은 기능이 제공되고, 가독성이 좋아 추천하고 있는 느낌이다.

Declarative Pipeline 문법

declarative pipeline은 pipeline{} 블록 안에 선언되어야한다. (groovy 구문과 동일한 규칙을 따른다.)

  • section - 하나 이상의 directive 또는 step 을 포함한다.
    • agent - 젠킨스는 master와 slave node로 나뉘는데 여기서 어떤 젠킨스가 일을 할지 지정, 최상위의 agent는 필수지만      section 내의 agent는 옵션
    • post - stage가 실행 완료 시 실행되는 추가 단계, post는 여러 조건 블록을 이용하여 stage 완료 상태에 따라 실행할 수 있다.
    • stages - 하나 이상의 stage를 포함해야한다, 파이프라인의 작업을 정의
    • steps - stage 에서 일련의 실행을 정의
  • directive
    • environment - pipeline또는 stage에 키 - 값 형태의 환경변수 지정, credentials() 메서드를 통해 콘솔(Global credentials)에서 생성한  자격 증명 기능 제공
    • options - pipeline또는 stage에 여러가지 옵션을 부여 (참고)
    • parameters - pipeline 블록에서만 작성가능, pipeline실행시 파라미터를 입력받는다. (참고)
    • triggers - pipeline 블록에서만 작성가능, 언제 재 트리거 될것인지 지정. (참고)
    • stage - stages 블록 내에 작성가능, pipeline이 수행되는 모든 일들이 하나 이상의 stage에 작성된다.
    • tools - pipeline또는 stage에 작성가능, 빌드 시 사용할 maven, jdk, gradle 툴 정의
    • input - stage 내에 input을 사용하면 해당 단계에서 입력을 받을 수 있다. (참고)
    • when - stage가 실행될 조건을 정의, 하나 이상의 조건이 포함되어야한다. (참고)
pipeline {
    agent any // 아무 에이전트에서 해당 파이프라인 또는 stage를 실행함.
    tools { // 빌드 시 사용할 maven 정의
        maven 'apache-maven-3.0.1' 
    }
    options { // pipeline 전체의 실행 시간에 1시간 timeout 옵션 추가, 1시간 초과시 실행 종료
        timeout(time: 1, unit: 'HOURS') 
    }
    environment {  // pipeline 블록의 환경 변수 지정, 모든 단계에 적용됨
        CC = 'clang' 
    }
    stages { // stage 정의
        stage('Build') { // 'Build'stage 정의
            environment {  // 액세스에 필요한 자격 증명
                AN_ACCESS_KEY = credentials('my-predefined-secret-text') 
            }
            steps {
                // 'Build'stage의 step 정의
            }
        }
    }
    post {  // stage의 실행이 완료된 후 실행
        always { // stage의 완료 상태에 관계없이 실행

        }
    }
}

 

  • Sequential stages
    • stages의 내부에는 순차적으로 실행될 중첩된 stages가 있을 수 있다.
    • stage에는 stages, steps, parallel. matrix중 하나만 있어야한다.
    • 만약 stage가 parallel 또는 matrix 블록 내에 작성된 경우 해당 stage 는 parallel 또는 matrix를 포함할 수 없고, agent, tools, when 등의 다른 기능들만 사용할 수 있다.
  • Parallel 
    • jenkins의 job(stage)들을 병렬로 실행하기 위한 구문
    • failfast 옵션을 추가하면 stage가 하나라도 실패하면 강제로 모두 중단된다.
    • = pipeline 블록에 options{ parallelsAlwaysFailFast() } 을 추가해도 같은 효과를 볼 수 있다.
  • Matrix
    • stage에 병렬로 실행할 name-value 조합의 다차원 matrix를 사용할 수 있다.
    • 이러한 조합을 cell 이라 부르고 cell의 구성을 사용해 순차적으로 실행할 하나 이상의 stage를 포함할 수 있다.
    • parallel과 마찬가지로 failFast 사용 가능
    • axes 블록, stage 블록이 포함되어야하고, axes는 matrix의 각 축에 대한 값(axis)을 정의한다.
    • axes 블록은 하나 이상의 axis를 정의하고 axis는 name-value list 로 구성된다.
    • 잘못된 cell을 제거하기 위해 excludes 블록을 사용할 수 있다.
    • exclude 블록 내부에 정의된 axis의 조합과 일치 또는 일치하지 않는 cell 제외
pipeline {
    agent any
    options {
        parallelsAlwaysFailFast()  // 병렬 실행 stage 하나라도 실패 시 실행 종료
    }
    stages {
        stage('Non-Parallel Stage') {
            steps {
                echo 'This stage will be executed first.'
            }
        }
        stage('Parallel Stage') {
            when {
                branch 'master'
            }
            parallel { // 병렬 실행 블록
                stage('Branch A') {
                    agent {
                        label "for-branch-a"
                    }
                    steps {
                        echo "On Branch A"
                    }
                }
                stage('Branch B') {
                    agent {
                        label "for-branch-b"
                    }
                    stages {
                        stage('Nested 1') { // 충첩 stage
                            steps {
                                echo "In stage Nested 1 within Branch B"
                            }
                        }
                        stage('Nested 2') {
                            steps {
                                echo "In stage Nested 2 within Branch B"
                            }
                        }
                    }
                }
            }
            // matrix
            matrix {
                axes {
                    axis {
                        name 'PLATFORM'
                        values 'linux', 'mac', 'windows'
                    }
                    axis {
                        name 'BROWSER'
                        values 'chrome', 'edge', 'firefox', 'safari'
                    }
                    axis {
                        name 'ARCHITECTURE'
                        values '32-bit', '64-bit'
                    }
                }
                // Linux, Safari 조합 제외 / Edge이고, windows가 아닌 조합 제외.
                excludes {
                    exclude {
                        // 4 cells
                        axis {
                            name 'PLATFORM'
                            values 'mac'
                        }
                        axis {
                            name 'ARCHITECTURE'
                            values '32-bit'
                        }
                    }
                    exclude {
                        // 2 cells
                        axis {
                            name 'PLATFORM'
                            values 'linux'
                        }
                        axis {
                            name 'BROWSER'
                            values 'safari'
                        }
                    }
                    exclude {
                        // 3 more cells and '32-bit, mac' (already excluded)
                        axis {
                            name 'PLATFORM'
                            notValues 'windows'
                        }
                        axis {
                            name 'BROWSER'
                            values 'edge'
                        }
                    }
                }
                stages {
                    stage('Build') {
                        steps {
                            echo "Do Build for ${PLATFORM} - ${BROWSER}"
                        }
                    }
                    stage('Test') {
                        steps {
                            echo "Do Test for ${PLATFORM} - ${BROWSER}"
                        }
                    }
                }
            }
        }
    }
}

 

 

파이프라인 문법 공식 문서

파이프라인 용어사전