.gitlab-ci.yml關鍵詞完整解析(二)
.gitlab-ci.yml關鍵詞完整解析(二)
上次我們介紹了
script, image, artifacts ,tags, cache ,stage ,when ,only/except。
學習了這幾個關鍵詞的用法,就不難配置一條簡單的流水線。但如果要遇到更加複雜的業務場景,如微服務,流水線繼承,多流水線,等複雜場景,那麼只靠以上的幾個用法是無法實現的。下面我就再給大家講解其他幾個更加複雜的關鍵詞。
這次講解的關鍵詞有:
before_script, after_script, dependencies, environment, extends, include, interruptible ,parallel, rules ,trigger, services
before_script
before_script 關鍵詞是用於在每個任務之前執行的指令碼,但是會在artifacts恢復之後執行。你可以這樣定義一個全域性的before_script
default:
before_script:
- echo "Execute this script in all jobs that don't already have a before_script section."
也可以在一個任務中中單獨定義
job: before_script: - echo "Execute this script instead of the global before_script." script: - echo "This script executes after the job's `before_script`"
任務中的before_script會覆蓋全域性的before_script
after_script
after_script與before_script類似,用於定義多行指令碼,會在任務執行完成後執行,即使任務失敗也會被執行。如果任務被取消或者超時,after_script就不會被執行了,目前官方正在計劃這個特性。
可以定義全域性的,也可以定義區域性的
default: after_script: - echo "Execute this script in all jobs that don't already have an after_script section." job1: script: - echo "This script executes first. When it completes, the global after_script executes." job: script: - echo "This script executes first. When it completes, the job's `after_script` executes." after_script: - echo "Execute this script instead of the global after_script."
dependencies
dependencies關鍵詞是定義特定的job執行規則。預設artifacts是從當前階段產生,在後續的階段都會被下載,但我們可以使用dependencies關鍵詞來控制artifacts從哪裡下載,這裡有一個例子
build:osx:
stage: build
script: make build:osx
artifacts:
paths:
- binaries/
build:linux:
stage: build
script: make build:linux
artifacts:
paths:
- binaries/
test:osx:
stage: test
script: make test:osx
dependencies:
- build:osx
test:linux:
stage: test
script: make test:linux
dependencies:
- build:linux
deploy:
stage: deploy
script: make deploy
根據這個例子我們不難看出,
任務test:osx 依賴build:osx
任務test:linux 依賴 build:linux
這樣配置以後 任務test:linux 就不用等任務build:osx 執行完成在執行了,只需要等待任務build:linux完成
很好地利用了依賴關係來優化流水線的速率,前四個任務都執行完成後,才會執行最後一個部署的任務。
environment
environment是用於定義環境變數,可以是用k-v的方式定義,如
deploy to production:
stage: deploy
script: git push production HEAD:master
environment:
name: production
需要注意的是這裡定義的環境變數是不能在script值使用的。這個關鍵詞可以和review和merge搭配。
extends
這個關鍵詞可以使一個任務繼承另一個任務。
.tests:
script: rake test
stage: test
only:
refs:
- branches
rspec:
extends: .tests
script: rake rspec
only:
variables:
- $RSPEC
任務rspec 繼承了.tests任務,在流水線中.tests是一個隱藏的任務,在流水線中,以英文遠點開頭的任務名,都是隱藏的任務。不會被執行。 被rspec繼承後,相同的key會以rspec為準,rspec沒有的,而.tests有的,則合併到rspec中,
合併後的結果是
rspec:
script: rake rspec
stage: test
only:
refs:
- branches
variables:
- $RSPEC
使用這一個手段,可以寫一個模板,只要稍微改改就能後使用。非常適合大批量編寫流水線。
include
使用include可以匯入一個或多個額外的yaml檔案到你的CICD配置裡,這一你就可以將一個很長的流水線,分隔出來。使用include來引入。
也可以將幾個流水線中相同的配置,提取出來,公用。引入的副檔名 必須是.yaml或者.yml兩種,其他的不行。
include 關鍵詞下,有四個可選性,
local, 引入一個當前專案的檔案
file, 引入一個不同專案的檔案
remote, 引入一個公網檔案,
template, 引入一個由GitLab提供的模板
下面是幾個例子
include:
- local: '/templates/.gitlab-ci-template.yml'
include:
- project: 'my-group/my-project'
file: '/templates/.gitlab-ci-template.yml'
include:
- local: '/templates/.gitlab-ci-template.yml'
include:
- project: 'my-group/my-project'
ref: master
file: '/templates/.gitlab-ci-template.yml'
- project: 'my-group/my-project'
ref: v1.0.0
file: '/templates/.gitlab-ci-template.yml'
- project: 'my-group/my-project'
ref: 787123b47f14b552955ca2786bc9542ae66fee5b # Git SHA
file: '/templates/.gitlab-ci-template.yml'
include:
- remote: 'https://gitlab.com/awesome-project/raw/master/.gitlab-ci-template.yml'
trigger
trigger 是應對那些更加複雜的CICD流程,如多流水線,父子流水線
使用它可以定義一個下游的流水線,配置了trigger的任務是不能跑指令碼的,就是說不能定義script, before_script, 和 after_script.
專案這個是一個多專案流水線
rspec:
stage: test
script: bundle exec rspec
staging:
stage: deploy
trigger: my/deployment
流水線執行完test任務後就會去執行my/deployment專案的流水線
配置下游流水線式也可以執行分支
rspec:
stage: test
script: bundle exec rspec
staging:
stage: deploy
trigger:
project: my/deployment
branch: stablez
rules
rules是用於規定任務的執行規則,使用一個表示式,來規範那些任務執行,那些任務不執行.還可以在任務成功,或者失敗後,觸發另一個任務。
如下面這個例子
docker build:
script: docker build -t my-image:$CI_COMMIT_REF_SLUG .
rules:
- if: '$CI_COMMIT_BRANCH == "master"'
when: delayed
start_in: '3 hours'
allow_failure: true
如果當前的分支是master分支則任務執行就延遲3個小時,並且允許失敗。
rules的下面有是哪個可選屬性
- if 使用if表示式 新增或移除一個任務, 類似 only:variables.
- changes 根據某些個檔案是否改變來追加或移除一些任務。類似 only:changes.
- exists 根據是否存在特定檔案來追加或移除一些任務
if中可以使用CICD的所有預設變數,分支,來源,合併請求,commit,push web,schedule等。可以針對不用的情景配置不用的規則。
在看下這個例子
job:
script: echo "Hello, Rules!"
rules:
- if: '$CI_MERGE_REQUEST_TARGET_BRANCH_NAME == "master"'
when: manual
allow_failure: true
解釋起來並不複雜,一個判斷語句,二句賦值語句。即如果當前分支是master,在任務的執行方式改為手動,並且執行失敗。