Gitlab持續集成-(.gitlab-ci.yml)
從7.12版本開始,GitLab CI使用YAML文件(.gitlab-ci.yml)來管理項目配置。該文件存放於項目倉庫的根目錄,它定義該項目如何構建。
stages
stages
用來定義可以被job調用的stages。stages的規範允許有靈活的多級pipelines。stages中元素的順序決定了對應job的執行順序:
- 相同stage的job是並行執行的;
- 下一個stage的job在前一個stage的job成功完成後才開始執行;
- 如果.gitlab-ci.yml中沒有定義stages,那麽stages默認定義為build、test和deploy;
- 如果一個job沒有指定stage,那麽這個任務會分配到test stage。
variables
variables
用來定義變量,全局變量作用於所有job,也可以在指定的job中定義變量(優先級高於全局變量)
如果在job中想禁用全局定義的變量,可通過variables: {}
定義一個空的哈希值。
GitLab CI/CD內置變量
variables | 變量值 |
---|---|
CI_JOB_NAME | 對應的job_name |
GIT_STRATEGY | 指定git獲取代碼的方式(clone,fetch,none) |
jobs
jobs
用來定義了一組作業,其中必須包含script
語句。
job.stage(默認:test
)
job中指定的stage必須是stages中存在的元素
job.tags
指定該job所允許運行的Runner,必須在註冊Runner時設置Runner的tag
job.allow_failure
用於指定該job允許執行失敗,則如果執行失敗也不會影響下一個stage的執行。
job.script
script
是job中必須指定的語句,指定Runner所要執行的命令
job.before_script、job.after_script
指定script執行前/後所執行的命令,也可定義在全局模式,則在所有job中的script執行前/後都會執行。
job.artifacts
用於指定job執行成功後,將會被發送到Gitlab中的文件,且默認情況下job之間會根據stage的優先級自動下載之前所有stage中的artifacts。
artifacts.paths
:必選artifacts.name
:指定artifact的名稱,同時Gitlab上下載的文件名即為artifact_name.zipartifacts.when
:指定artifact上傳到Gitlab的條件(on_success[默認],on_failure,always)artifacts.expire_in
:指定artifact的過期時間(默認為30天),使用keep
可永久保存
job.dependencies
dependencies
用於在不同的job之間指定在不同的job之間傳遞artifacts,dependencies: []
可禁止該job下載artifacts
job.only、job.except
only
和except
是兩個參數用分支策略來限制jobs構建
only
和except
可同時使用。如果在一個job配置中同時存在,則同時有效;only
和except
可以使用正則表達式;only
和except
允許使用特殊的關鍵字:branches
,tags
和triggers
;
job.environment
environment
用於定義job部署到指定的運行環境中。
- environment.name:必選,指定environment名稱
- environment.url:可選,指定environment對應的URL,將在指定的environment頁面中添加一個鏈接按鈕指向該URL
特殊的YAML特性
<span id = "jump"> Hidden keys(jobs)</span>
如果想臨時disable某個job,不必註釋整個job定義的行,只需在job name前加一個
.
即可
.compile_centos:
stage: build_centos
tags:
- centos
script:
- echo "##### build library"
Anchors
錨點可用於在文件中復制或繼承配置,一般與Hidden keys(jobs)提供的job模版搭配使用。
.job_template: &job_definition #job中定義一個anchor:job_definition
image: ruby:2.1
services:
- postgres
- redis
test1:
<<: *job_definition #合並anchor:job_definition中的模版內容
script:
- test1 project
test2:
<<: *job_definition
script:
- test2 project
最終實現的效果如下:
.job_template:
image: ruby:2.1
services:
- postgres
- redis
test1:
image: ruby:2.1
services:
- postgres
- redis
script:
- test1 project
test2:
image: ruby:2.1
services:
- postgres
- redis
script:
- test2 project
Skipping jobs
如果你的commit信息中包含
[ci skip]
或者[skip ci]
,不論大小寫,那麽這個commit將會創建但是jobs也會跳過。
example:
以下示例為編譯nginx的上傳模塊nginx-upload並測試驗證上傳功能,驗證成功後將自動將編譯好的文件打包通過curl上傳到指定的文件服務器。其中只有在非master的branches中提交代碼才會執行build和test的stage,只有在打tag後才會執行deploy,且需要手動在gitlab上執行。
variables:
DIR: nginx
TOPNODE: package
.function: &function |
function build() {
echo "execute function:build"
chmod +x auto/configure
sh build.sh
}
function changelog() {
echo "execute function:changelog"
git log --graph -n 3 --name-status --pretty="%h -[%cd] - <%an> %s" > CHANGELOG
}
function test() {
echo "execute function:test"
sudo \cp modules/nginx-upload-module-master/nginx.conf /etc/nginx/nginx.conf
sudo sed -i ‘/error_log/,/working_directory/d‘ /etc/nginx/nginx.conf
if [ -f /run/nginx.pid ];then sudo nginx -s reload;else sudo nginx;fi
sudo rm -rf /tmp/{0,1,2,3,4,5,6,7,8,9} && sudo mkdir /tmp/{0,1,2,3,4,5,6,7,8,9} && sudo chown -R nginx. /tmp/{0,1,2,3,4,5,6,7,8,9}
sudo echo nginx_upload > test && curl -F "filename=@test" http://localhost/upload
sudo find /tmp/{0,1,2,3,4,5,6,7,8,9} -type f -exec grep nginx_upload {} \;
}
function artifacts() {
echo "execute function:artifacts"
URL="https://xxx.com/upload?dir=${DIR}/${VERSION}&override=1&topNode=${TOPNODE}"
echo "push the artifacts:nginx_${VERSION}.tar.gz to $URL"
tar zcf /tmp/nginx_${VERSION}.tar.gz --exclude=".git*" --exclude=build .
curl -F "filename=@/tmp/${DIR}_${VERSION}.tar.gz" "$URL"
echo "push the CHANGELOG to $URL"
curl -F "filename=@CHANGELOG" "$URL"
}
function deploy() {
echo "execute function:deploy"
}
function clean() {
echo "execute function:clean"
if [ -f /run/nginx.pid ];then sudo kill `cat /run/nginx.pid`;fi
sudo rm -rf /tmp/{0,1,2,3,4,5,6,7,8,9} /tmp/nginx_${version}.tar.gz
}
#########only the section above need to be modify #################
before_script:
- VERSION=`head -n1 version`
- *function
stages:
- build
- test
- deploy
build:
stage: build
only:
- branches
except:
- master
script:
- build
- changelog
test:
stage: test
variables:
GIT_STRATEGY: none
only:
- branches
except:
- master
script:
- test
- artifacts
- clean
.job_template: &deploy_template
stage: deploy
variables:
GIT_STRATEGY: none
only:
- tags
script:
- deploy
- delete
when: manual
staging:
<<: *deploy_template
environment:
name: staging
production:
<<: *deploy_template
environment:
name: production
Gitlab持續集成-(.gitlab-ci.yml)