1. 簡介
Pipeline 支持兩種語法:Declarative Pipeline(在 Pipeline 2.5 中引入,結構化方式)和 Scripted Pipeline。Pipeline 最基本的部分是 “step”。step 告訴 Jenkins 要做什么,並且作為 Pipeline 的基本構建塊。
為與 BlueOcean 腳本編輯器兼容,通常建議使用 Declarative Pipeline 的方式進行編寫。
2. Declarative Pipeline
Declarative Pipeline中有效的基本語句和表達式遵循與Groovy語法相同的規則 ,但有以下例外:
- Pipeline的頂層必須是塊,具體來說是:pipeline { }
- 沒有分號作為語句分隔符。每個聲明必須在自己的一行
- 塊只能包含章節Sections,指令Directives, 步驟Steps或賦值語句。
- 屬性引用語句被視為無參數方法調用。所以例如,input被視為input()
Declarative Pipeline語法- Sections(章節)
Sections 通常包含一個或多個 Directives 或 Steps
關鍵字 | 意義 | 常見選項 |
---|---|---|
agent | 作用:告知Jenkins選擇那台節點機器去執行Pipeline代碼。這個指令在 pipeline 塊頂層必須定義。 | any---任何 none---管道不指定,模塊,步驟中指定 label---指定標簽 node---agent { node { label 'labelName' } },等同於 agent { label 'labelName' },但 node 允許其他選項(如 customWorkspace) docker--動態供應一個 docker 節點,docker 還可以接受args,直接傳遞給 docker run 調用 dockerfile---使用從 Dockerfile 源存儲庫中包含的容器來構建執行。為使用此選項,Jenkinsfile 必須從 Multibranch Pipeline 或 “Pipeline from SCM"加載。 kubernetes |
post | 作用:post部分定義了一個或多個附加步驟,一般用來發送消息或者郵件通知。在 Pipeline 或 stage 運行結束時操作。 | 在post代碼塊區域,支持多種條件指令,這些指令有always,changed,failure,success,unstable,和aborted。 |
stages | 允許出現至少一次stages。一個stages下可以包含多個stage,一個stage 下至少有一個steps。 | |
steps | 只支持steps,不支持在steps {…} 里面嵌套寫step{…}。 |
Example 1
pipeline {
agent any
stages {
stage('Build') {
steps {
println "Build"
}
}
stage('Test') {
steps {
println "Test"
}
}
stage('Deploy') {
steps {
println "Deploy"
}
}
}
}
Declarative Pipeline語法- Directives(指令)
關鍵字 | 意義 | 常見選項 |
---|---|---|
environment | 設置環境變量,指定一系列鍵值對 | credentials() |
options | 允許在Pipeline中配置特定於Pipeline的內置選項。 | buildDiscarder, checkoutToSubdirectory, disableConcurrentBuilds, newContainerPerStage, overrideIndexTriggers, preserveStashes, quietPeriod, retry, skipDefaultCheckout,skipStagesAfterUnstable, timeout,timestamps |
parameters | 提供了用戶在觸發Pipeline時應提供的參數列表,可通過頁面配置 | string, text, booleanParam, choice, file, password |
triggers | 定義了觸發管道的自動方式。 對於與GitHub或BitBucket等源集成的管道,可能不需要觸發器,因為基於webhooks的集成可能已經存在。 目前可用的觸發器是cron,pollSCM和upstream,可通過頁面配置 | cron, pollSCM, upstream |
stage | 位於階段部分。Pipeline所做的所有實際工作都將包含在一個或多個階段指令中。 | |
tools | 定義自動安裝和放置工具的部分PATH。如果agent none指定,這將被忽略。引用的工具名必須在Manage Jenkins → Global Tool Configuration中預定義 | maven,jdk,gradle |
input | 等待用戶輸入,根據輸入值繼續后續的流程 | message, id, ok, submitter, submitterParameter, parametersv |
when | 符合條件,則執行。when指令必須至少包含一個條件。 | beforeAgent, branch, buildingTag, changelog, changeset, changeRequest, environment, equal, expression, tag, not, allof, anyof |
Example 2 input
pipeline {
agent any
stages {
stage('Example') {
input {
message "Should we continue?"
ok "Yes, we should."
submitter "alice,bob"
parameters {
string(name: 'PERSON', defaultValue: 'Mr Jenkins', description: 'Who should I say hello to?')
}
}
steps {
echo "Hello, ${PERSON}, nice to meet you."
}
}
}
}
Example 3 when
pipeline {
agent any
environment {
quick_test = false
}
stages {
stage('Example Build') {
steps {
script {
echo 'Hello World'
}
}
}
stage('Example Deploy') {
when {
expression {
return (quick_test == “true” )
}
}
steps {
echo 'Deploying'
}
}
}
}
Declarative Pipeline語法- 多個stage的關系:順序和並行
順序stage
Example 4
pipeline {
agent none
stages {
stage('Non-Sequential Stage') {
agent {
label 'for-non-sequential'
}
steps {
echo "On Non-Sequential Stage"
}
}
stage('Sequential') {
agent {
label 'for-sequential'
}
environment {
FOR_SEQUENTIAL = "some-value"
}
stages {
stage('In Sequential 1') {
steps {
echo "In Sequential 1"
}
}
stage('In Sequential 2') {
steps {
echo "In Sequential 2"
}
}
stage('Parallel In Sequential') {
parallel {
stage('In Parallel 1') {
steps {
echo "In Parallel 1"
}
}
stage('In Parallel 2') {
steps {
echo "In Parallel 2"
}
}
}
}
}
}
}
}
並行stage
failFast true,只要有一個不通過,就中止運行pipeline下面的代碼
Example 4
pipeline {
agent any
stages {
stage('Non-Parallel Stage') {
steps {
echo 'This stage will be executed first.'
}
}
stage('Parallel Stage') {
when {
branch 'master'
}
failFast true
parallel {
stage('Branch A') {
agent {
label "for-branch-a"
}
steps {
echo "On Branch A"
}
}
stage('Branch B') {
agent {
label "for-branch-b"
}
steps {
echo "On Branch B"
}
}
stage('Branch C') {
agent {
label "for-branch-c"
}
stages {
stage('Nested 1') {
steps {
echo "In stage Nested 1 within Branch C"
}
}
stage('Nested 2') {
steps {
echo "In stage Nested 2 within Branch C"
}
}
}
}
}
}
}
}
3. Scripted Pipeline
Scripted Pipeline 是基於 groovy 的一種 DSL 語言,與 Declarative pipeline 相比提供了更巨大的靈活性和可擴展性。
流程控制 Flow Control
依賴於Groovy表達式,例如if/else條件,try/catch/finally塊
與普通Groovy的區別 Differences from plain Groovy
由於 pipeline 的個性化需求,比如在重新啟動 jenkins 后要求 pipeline 腳本仍然可以運行,那么 pipeline 腳本必須將相關數據做序列化。這個設計要求,一些Groovy習慣用法集合並不完全支持,例如 collection.each { item → /* perform operation */ }