1. 程式人生 > 其它 >Jenkins Pipeline 常用指令

Jenkins Pipeline 常用指令

Groovy 背景

Jenkins 流水線(Pipeline 是 Jenkins2.X 最核心的特性,幫助 Jenkins 實現從 CI 到 CD 與DevOps 的轉變,可支援複雜流程的編排與視覺化) 是一套外掛,可通過 Jenkinsfile 執行,支援指令碼式(Script)和宣告式(Declarative)兩種,其中指令碼式可通過 Groovy 語法編寫執行過程,宣告式需要用 script {}包裹使用 Groovy 語句。

宣告式指令簡介

1.最外層必須由 pipline{ //do something }來進行包裹
2.不需要分號作為分隔符,每個語句獨佔一行
3.不能直接使用 groovy 語句(例如迴圈判斷等),需要被 script {}包裹

  • pipeline :宣告其內容為一個宣告式的 pipeline 指令碼
  • agent:執行節點(支援 any,none,label,docker,dockerfile)
  • stages:階段集合,包裹所有的階段(例如:打包,部署等各個階段)
  • stage:階段,被 stages 包裹,一個 stages 可以有多個 stage
  • steps:步驟,為每個階段的最小執行單元,被 stage 包裹
// 示例
pipeline {
    agent any
    stages {
        stage('Example') {
            steps { 
                echo 'Hello World'
            }
        }
    }
}

environment

  • 在 pipline 塊內,為全域性變數,對所有階段和步驟生效
  • 在 stage 階段內,為區域性變數,只對階段和步驟生效

withEnv

  • 一般使用在子步驟下
// 示例
pipeline {
  agent any
  stages {
    stage('Example') {
      environment {
        deploy = 'testing'
      }
      steps {
        echo env.NAME
        echo "${NAME}"
        echo "${deploy}"
        echo "$CC"
        withEnv(['name=tester']) {
          echo "$name"
        }
      }
    }
  }
  environment {
    CC = 'clang'
  }
}

post (通常定義在 pipeline 末端)

  • always: 始終執行
  • aborted: 終止時執行
  • failure: 失敗時執行
  • success: 成功是執行
  • unsuccessful :不成功時執行
  • cleanup :其他 post 過程執行完畢後執行
// 示例
pipeline {
    agent any
    stages {
        stage('Example') {
            steps { 
                error '構建失敗:這是一個自定義的錯誤資訊'
            }
        }
    }
    post {
      failure {
        echo "this is a error"
      }
    }
}

when (使用在 stage 內)

  • branch: 分支匹配時執行(when { branch 'master' })
  • branch: 分支匹配時執行(when { branch 'master' })
  • environment: 變數為給定值時執行(when { environment name: 'DEPLOY_ENV', value: 'production' })
  • expression: Groovy表示式求值為true時執行(when { expression { return params.DEBUG_BUILD } })
  • not: 巢狀條件為false時執行(when { not { branch 'master' } })
  • allOf: 巢狀的條件都為真時執行(when { allOf { branch 'master'; environment name: 'DEPLOY_ENV', value: 'production' } })
  • anyOf: 至少一個巢狀的條件為真時執行(when { anyOf { branch 'master'; branch 'staging' } })
// 示例
pipeline {
    agent any
    stages {
        stage('DEPLOY_ENV') {
            when { environment name: 'DEPLOY_ENV', value: 'production' }
            steps { 
                echo "production 環境正在執行"
            }
        }
    }
}

Parallel (並行)

// 示例
pipeline {
    agent any
    stages {
        stage('Parallel Stage') {
            when {
                branch 'master'
            }
            parallel {
                stage('testing') {
                    steps {
                        echo "depoly testing"
                    }
                }
                stage('staging') {
                    steps {
                        echo "depoly staging"
                    }
                }
            }
        }
    }
}

options (選項)

  • 常用的有 timeout()、retry()
// 示例
pipeline {
  agent any
  options {
    retry(3) // 重試
    timeout(time:10, unit:"SECONDS") // 超時
  }
  stages {
    stage('demo'){
      steps{
          sh 'echo hello'
          sleep(15)
      }
    }
  }
}

steps 中的一些操作

  • error:丟擲異常,中斷整個pipeline
  • timeout: 超時
  • waitUntil: 迴圈執行閉包內容,直到返回true,通常與timeout一起使用
  • retry:失敗重試
  • sleep:睡眠,預設單位秒
// 示例
pipeline{
    agent any
    stages{
        stage('stash'){
            parallel('測試') {
              stage('輪詢') {
                steps{
                  timeout(time:10, unit:"SECONDS"){
                    waitUntil{
                      script{
                        def rs = sh script: 'docker version', returnStatus: true     
                        return (rs == 0)
                      }
                    }
                  }
                }
              }
              stage('重試') {
                steps{
                retry(3){
                  script{
                      sh script: 'curl https://www.baidu.com', returnStatus: true
                    }
                  sleep(3)
                }
              }
            }

            stage('錯誤') {
                steps{
                  retry(3){
                    error("執行失敗")
                  }
              }
            }
          }
        }
    }
}

input (暫停執行,等待確認)

// 示例
pipeline {
  agent any
  stages {
    stage('Example') {
      input {
        message 'Should we continue?'
        parameters {
          string(name: 'PERSON', defaultValue: 'Mr Jenkins', description: 'Who should I say hello to?')
        }
      }
      steps {
        echo "Hello, ${PERSON}, nice to meet you."
        input(message: '是否繼續執行構建', parameters: [ choice(name:'depoly',description:'部署環境',choices:['testing','staging','production'])])
      }
    }
  }
}

script (指令碼使用)

// 示例
def test = "test"
pipeline {
  agent any
  stages {
    stage('環境變數') {
      steps {
        sh 'pwd'
        sh "echo ${NAME}"
        script {
            if ("${NAME}" == "/root/test") {
              echo "pass"
            } else if ("${NAME}" == "${test}") {
              echo "pass"
            } else {
              error("環境變數有誤 ${NAME}")
            }
        }
      }
    }
  }
}

指令碼式案例

  • 最外層有 node{} 包裹
// 示例
def TEST_PROJECT_NAME=""
def deployments = ["testing", "staging", "production"]
def run(stepName) { 
   retry(3){
        TEST_PROJECT_NAME = sh(script: "openssl rand  -hex 4",returnStdout: true).trim()
        sh (
            script: "echo ${TEST_PROJECT_NAME}",
            label: "開始 ${stepName} 環境API測試"
        )
   }
}

node {
    deployments.each{ param -> 
            stage("$param") {
                run("$param")
        }
    }
}

拓展

build

  • build 用法,支援觸發另一個 job 構建
// 示例
pipeline {
    agent any
    stages {
        stage('Example') {
            steps { 
                echo 'Hello World'
            }
        }
    }
    post {
        success {
	        script {
	            println "執行成功"
	            jobB = build job: 'pipeline'
	            println("構建狀態: "+jobB.getResult())
	        }
	    }
	}
}