3指令说明(Directives)
显然,基本结构满足不了现实多变的需求。所以,Jenkins pipeline通过各种指令(directive)来丰富自己。指令可以被理解为对Jenkins pipeline基本结构的补充。指令是帮助pipeline更容易的执行命令,可以理解为一个封装好的公共函数和方法,提供给pipeline使用.
Jenkins pipeline支持的指令有:
- environment:用于设置环境变量,可定义在stage或pipeline部分。
- tools:可定义在pipeline或stage部分。它会自动下载并安装我们指定的工具,并将其加入PATH变量中。
- input:定义在stage部分,会暂停pipeline,提示你输入内容。
- options:用于配置Jenkins pipeline本身的选项,比如options {retry(3)}指当pipeline失败时再重试2次。options指令可定义在stage或pipeline部分。
- parallel:并行执行多个step。在pipeline插件1.2版本后,parallel开始支持对多个阶段进行并行执行。
- parameters:与input不同,parameters是执行pipeline前传入的一些参数。
- triggers:用于定义执行pipeline的触发器。
- when:当满足when定义的条件时,阶段才执行。
在使用指令时,需要注意的是每个指令都有自己的“作用域”。如果指令使用的位置不正确,Jenkins将会报错。
3.1 Environment/ withEnv
指令说明:environment指令指定一系列键值对,这些键值对将被定义为所有step或stage-specific step的环境变量,具体取决于environment指令在Pipeline中的位置。
该指令支持一种特殊的方法credentials(),可以通过其在Jenkins环境中的标识符来访问预定义的凭据。
对于类型为“Secret Text”的凭据,该 credentials()方法将确保指定的环境变量包含Secret Text内容;对于“标准用户名和密码”类型的凭证,指定的环境变量将被设置为username:password。
pipeline{
agent any
environment {
P1="parameters 1"
AN_ACCESS_KEY = credentials('my-prefined-secret-text')
}
stages{
stage("stage2"){
environment {
P2="parameters 2"
}
steps{
echo "$P1"
echo "$P2"
}
}
}
}
withEnv使用案例:
pipeline{
agent any
stages{
stage("init") {
steps{
withEnv(['E1=abc']) {
Echo env.E1 }
script {
println "test with withEnv feature"
}
}
}
}
}
这个用withEnv添加多个环境变量.
3.2 options
指令说明:options指令允许在Pipeline本身内配置Pipeline专用选项。Pipeline本身提供了许多选项,例如buildDiscarder,但它们也可能由插件提供,例如 timestamps。
是否必须:非必须
参 数:可选参数
作 用 域:整个pipeline模块,或整个stage模块
options指令能够提供给脚本更多的选项:
- buildDiscarder:保留指定数量的流水线构建记录
用法:options { buildDiscarder(logRotator(numToKeepStr: '1')) } - disableConcurrentBuilds:不允许并行执行流水线,防止同时访问共享资源等
用法:options { disableConcurrentBuilds() } - skipDefaultCheckout:跳过默认设置的代码check out
用法:options { skipDefaultCheckout() } - skipStagesAfterUnstable:一旦构建状态变得UNSTABLE,跳过该阶段
用法:options { skipStagesAfterUnstable() } - checkoutToSubdirectory:在工作空间的子目录进行check out
用法:options { checkoutToSubdirectory('children_path') } - timeout:设置jenkins运行的超时时间,超过超时时间,job会自动被终止
用法:options { timeout(time: 1, unit: 'MINUTES') }
说明:time:整型,休眠时间。
unit(可选):时间单位,支持的值有NANOSECONDS、MICROSECONDS、MILLISECONDS、 SECONDS、MINUTES(默认)、HOURS、DAYS。
- retry :设置retry作用域范围失败后重试,如retry(3)表示失败后重新执行次数2
用法:options { retry(3) } - timestamps:为控制台输出增加时间戳
用法:options { timestamps() }
- newContainerPerStage:当agent为docker或dockerfile时,指定在同一个Jenkins节点上,每个stage都分别运行在一个新的容器中,而不是所有stage都运行在同一个容器中。
用法:options { newContainerPerStage() }
备注:当options作用在stage内部的时候,可选的只能是跟stage相关的选项(skipDefaultCheckout、timeout、retry、timestamps)
以其中几个作为例子
pipeline{
agent any
options {
timestamps()
disableConcurrentBuilds()
}
stages{
stage("stage1"){
options { timeout(time:1,unit:'MINUTES')
retry(2)
}
steps{
echo "beging===================="
sh "xxx.sh"
}
}
}
}
3.3 parameters
指令说明:parameters 指令提供用户在触发 Pipeline 时应提供的参数列表,也就是在以往的free style风格中最常用到的参数化构建,我们不必在每次新建项目之后,一步一步在web界面中配置需要的参数,而是可以直接通过声明式进行参数化风格定义,这样极大简化了配置工作。
- 作用域:被最外层pipeline所包裹,并且只能出现一次,参数可被全局使用
- 好处:使用parameters好处是能够使参数也变成code,达到pipeline as code,pipeline中设置的参数会自动在job构建的时候生成,形成参数化构建
- 目前只支持[booleanParam, choice, credentials, file, text, password, run, string]这几种参数类型,其他高级参数化类型还需等待社区支持
parameters 指令支持以下几种常用类型:
string,字符串类型。
以往常常通过这个参数,来定义手动构建时输入将要构建的代码分支,那么这里可以用如下方式表达:
pipeline {
agent any
parameters {
string(name: 'branch', defaultValue: 'master', description: '请输入将要构建的代码分支')
}
}
注意:这种声明定义之后,需要手动构建一次,然后配置就会自动落位到原来熟悉的参数化构建中了。
choice,选项参数类型。
以往经常会选用这个参数,用于指定构建的方向是部署还是回滚,多个参数有两种表达方式。
其一:
pipeline {
agent any
parameters {
choice(name: 'mode', choices: ['deploy', 'rollback'], description: '选择方向!')
}
}
其二:
pipeline {
agent any
parameters {
choice(name: 'ENV_TYPE', choices: 'test\n\pre\nprod', description: '请选择部署的环境')
}
}
以上两种参数,做一个简单的配置实验,首先准备如下伪代码:
pipeline{
agent any
parameters {
string(name: 'branch', defaultValue: 'master', description: '请输入将要构建的代码分支')
choice(name: 'mode', choices: ['deploy', 'rollback'], description: '选择方向!')
}
stages {
stage('test') {
steps{
script {
sh "java -version"
}
}
}
}
}
创建一个新的pipeline风格的项目,将如上代码填写进入,点击构建,然后参数就会落位到对应的位置了。
接着继续介绍这里的参数。
booleanParam,布尔值参数
就是定义一个布尔类型参数,用户可以在 Jenkins UI 上选择是还是否,选择是表示代码会执行这部分,如果选择否,会跳过这部分。
pipeline {
agent any
parameters {
booleanParam(name: 'DEBUG_BUILD', defaultValue: true, description: '')
}
}
text,文本参数
文本(text)的参数就是支持写很多行的字符串。
pipeline {
agent any
parameters {
text(name: 'Deploy_text', defaultValue: 'One\nTwo\nThree\n', description: '')
}
}
password,密码参数
密码(password)参数就是在 Jenkins 参数化构建 UI 提供一个暗文密码输入框,所有需要脱敏的信息,都可以通过这个参数来配置。
Pipeline {
agent any
parameters {
password(name: 'PASSWORD', defaultValue: 'SECRET', description: 'A secret password')
}
}
如上参数已经基本上可以满足日常需求,思路大概就是通过Jenkinsfile的配置,部署仍旧沿用以往常规的手动部署的方式,这种方式在高效率持续构建方面,似乎已经不大适合,所以以后可以与input参数配合使用,这里不展开,以后可专门列一篇文章来讲。
3.4 triggers
指令说明:triggers:触发器是自动化运行pipeline的方法
- 作用域:被pipeline包裹,在符合条件下自动触发pipeline
目前包含三种自动触发的方式:
第一种:cron
- 作用:以指定的时间来运行pipeline
- 用法:triggers { cron('*/1 * * * *') }
第二种:pollSCM
- 作用:以固定的时间检查代码仓库更新(或者当代码仓库有更新时)自动触发pipeline构建
- 用法:triggers { pollSCM('H */4 * * 1-5') }或者triggers { pollSCM() }(后者需要配置post-commit/post-receive钩子)
第三种:upstream
- 作用:可以利用上游Job的运行状态来进行触发
- 用法:triggers { upstream(upstreamProjects: 'job1,job2', threshold: hudson.model.Result.SUCCESS) }
pipeline{
agent any
//说明:当test_8或者test_7运行成功的时候,自动触发
triggers { upstream(upstreamProjects: 'test_8,test_7', threshold: hudson.model.Result.SUCCESS) }
stages{
stage("stage1"){
steps{
echo "hello"
}
}
}
}
3.4.1定时执行-cron
*指令说明:
*基本代码段:cron(‘32 * * * *’) 或 cron ‘32 * * * * ’
*参数说明:
举例说明
每15分钟构建一次:H/15 * * * * 或*/5 * * * *
每天8点构建一次:0 8 * * *
每天8点~17点,两小时构建一次:0 8-17/2 * * *
周一到周五,8点~17点,两小时构建一次:0 8-17/2 * * 1-5
每月1号、15号各构建一次,除12月:H H 1,15 1-11 *
*/5 * * * * (每5分钟检查一次源码变化)
0 2 * * * (每天2:00 必须build一次源码
每个部分代表的含义以及取值范围
分钟,取值范围(0~59):若其他值不做设定,则表示每个设定的分钟都会构建
如:5 * * * * ,表示每个小时的第5分钟都会构建一次
小时,取值范围(0~23):若其他值不做设定,则表示每个设定小时的每分钟都会构建
如:* 5 * * * ,表示在每天5点的时候,一小时内每一分钟都会构建一次
日期,取值范围(1~31):若其他值不做设定,则表示每个月的那一天每分钟都会构建一次
如:* * 5 * *,表示在每个月5号的时候,0点开始每分钟构建一次
月份,取值范围(1~12):若其他值不做设定,则表示每年的那个月每分钟都会构建一次
如:* * * 5 *,表示在每年的5月份,1号0点开始每分钟构建一次
星期,取值范围(0 ~ 7):若其他值不做设定,则表示每周的那一天几每分钟都会构建一次
如:* * * * 5,表示每周五0点开始每分钟构建一次
*应用案例:
pipeline {
agent any
triggers {
cron('32 * * * *')
}
stages {
stage('Nightly build') {
steps {
echo "这是一个耗时的构建,每小时32分构建"
}
}
}
}
3.4.2轮询执行-pollSCM
指令说明:轮询代码仓库是指定期到代码仓库询问代码是否有变化,如果有变化就执行。
配置条件:存在轮询对象设置。
场景要求:比如场景时,pipe脚本定时监控SVN上资源是否发生改变,如果SVN上的资源有变高,就触发pipeline脚本去checkout更新资源。
第一种通过UI页面配置:
配置如下面两张图:
第一步:设置触发器,如图1
第二步,设置被监控代码库,如图2
第二种是纯代码实现:
注意:这个脚本必须先手动构建一次后才生效。
注意:这个脚本必须先手动构建一次后才生效。
注意:这个脚本必须先手动构建一次后才生效。
代码如下:
pipeline {
agent any
triggers {
// 每分钟判断一次代码是否有变化
pollSCM("H/1 * * * *")
}
stages{
stage('stage1'){
steps{
echo "this is pollscon"
checkout([$class: 'SubversionSCM', additionalCredentials: [], excludedCommitMessages: '', excludedRegions: '', excludedRevprop: '', excludedUsers: '', filterChangelog: false, ignoreDirPropChanges: false, includedRegions: '', locations: [[cancelProcessOnExternalsFail: true, credentialsId: 'f14941ce-4fd0-436e-a3e2-3dbb56851840', depthOption: 'infinity', ignoreExternalsOption: true, remote: 'https://10.200.0.2/ZQ/KTMP/TEST/Src/bin/remote']], quietOperation: true, workspaceUpdater: [$class: 'UpdateUpdater']])
}
}
}
}
注意:这个脚本必须先手动构建一次后才生效。
其中checkout([$class: 'SubversionSCM', additionalCredentials: [], excludedCommitMessages: '', excludedRegions: '', excludedRevprop: '', excludedUsers: '', filterChangelog: false, ignoreDirPropChanges: false, includedRegions: '', locations: [[cancelProcessOnExternalsFail: true, credentialsId: 'f14941ce-4fd0-436e-a3e2-3dbb56851840', depthOption: 'infinity', ignoreExternalsOption: true, remote: 'https://10.200.0.2/ZQ/KTMP/TEST/Src/bin/remote']], quietOperation: true, workspaceUpdater: [$class: 'UpdateUpdater']]),这节代码是通过代码段生产器生产的,如下截图:
3.4.3根据上游来执行-upstream
指令说明:当B任务的执行依赖A任务的执行结果时,A就被称为B的上游任务。在Jenkins 2.22及以上版本中,trigger指令开始支持upstream类型的触发条件。upstream的作用就是能让B pipeline自行决定依赖哪些上游任务。
// job1和job2都是任务名
triggers {
upstream(upstreamProjects: "job1,job2", threshold: hudson.model.Result.SUCCESS)
}
当upstreamProjects参数接收多个任务时,使用,分隔。threshold参数是指上游任务的执行结果是什么值时触发。hudson.model.Result是一个枚举,包括以下值:
ABORTED:任务被手动中止。 FAILURE:构建失败。 SUCCESS:构建成功。 UNSTABLE:存在一些错误,但不至于构建失败。 NOT_BUILT:在多阶段构建时,前面阶段的问题导致后面阶段无法执行。
举例:
pipeline{
agent any
triggers {
upstream(upstreamProjects: "Example1-构建任意脚本,Example2-触发器-定时执行-cron", threshold: hudson.model.Result.SUCCESS)
}
stages{
stage('上游触发'){
steps{
echo 'start bulid due to before project'
}
}
}
}
注意:需要手动触发一次任务,让Jenkins加载pipeline后,trigger指令才会生效。
3.4.3 gitlab事件触发
指令说明:这个才是真正更多应用场景的,大多时候,我们都默认将项目配置为,开发者提交某些分支,然后自动触发对应的构建。传统方式下,需要比较复杂的几步配置,但是在pipeline中也可以通过代码形式对这种触发器进行配置,实在是一大便利神器。
到这儿,基本上每个项目在Jenkins当中的耦合,我们可以看到,越来越少了,我们运维人员,只需专注维护 Jenkinsfile,然后创建对应项目,只需在流水线处配置代码url即可。
这里先简单做一下示例介绍,并不展开,后边也会专门写篇文章来介绍这种应用方式,注意,gitlab触发Jenkins的构建需要依赖Gitlab插件,而并不需要插件当中列出来的所谓的gitlab hook。
pipeline {
agent any
triggers{
gitlab( triggerOnPush: true,
triggerOnMergeRequest: true,
branchFilterType: 'All',
secretToken: "028d848ab64f")
}
stages {
stage('build') {
steps {
echo '提交触发的构建'
}
}
}
}
对于触发器所用到的参数,这里简单介绍一下:
triggerOnPush:当Gitlab触发push事件时,是否执行构建。
triggerOnMergeRequest:当Gitlab触发mergeRequest事件时,是否执行构建。
branchFilterType:只有符合条件的分支才会触发构建,必选,否则无法实现触发。
可选参数有:
All:所有分支。
NameBasedFilter:基于分支名进行过滤,多个分支名使用逗号分隔。
includeBranchesSpec:基于branchFilterType值,输入期望包括的分支的规则。
excludeBranchesSpec:基于branchFilterType值,输入期望排除的分支的规则。
RegexBasedFilter:基于正则表达式对分支名进行过滤。
sourceBranchRegex:定义期望的通过正则表达式限制的分支规则。
所有分支这个选项不用解释了,其余两个选项怎么用,才是比较重要,而且可能在实际生产中,经常或者一定会用到的。但是网上的文章,乃至于Jenkins的官方文档,也都只是像上边那样,提到了有这样的语法规则存在,并没有任何一个地方给出示例的,当我去到Gitlab插件的官方地址后,发现了下边第一种语法的简单示例,仍旧没有我想要的基于正则限制的那种,于是,各位注意(因为搜遍全网也没有的示例),示例如下。
如果只接受固定分支的触发请求,语法如下:
triggers{
gitlab( triggerOnPush: true,
triggerOnMergeRequest: true,
branchFilterType: "NameBasedFilter",
includeBranchesSpec: "release",
secretToken: "${env.git_token}")
}
如果想通过正则匹配到某些分支进行触发,语法如下:
triggers{
gitlab( triggerOnPush: true,
triggerOnMergeRequest: true,
branchFilterType: "RegexBasedFilter",
sourceBranchRegex: "test.*",
secretToken: "${env.git_token}")
}
注意:所有触发器同样都需要先手动执行一次,让Jenkins加载其中的配置,对应的指令才会生效。
3.5 tools
指令说明:通过tools可自动安装工具,并放置环境变量到PATH。如果agent none,这将被忽略。引用的工具需要在管理页面的全局工具配置里配置过。
配置条件:进入Manage Jenkins→Global Tool Configuration,配置对应软件的信息。详情见章节5. 构建工具。
脚本如下:
pipeline {
agent any
tools {
maven 'apache-maven-3.0.1'
}
stages {
stage('Example') {
steps {
sh 'mvn --version'
}
}
}
}
3.6 input
指令说明:该input指令允许在一个stage{…}显示提示输入等待。在inpt{…}写一些条件,然后用户触发构建这个job,但是这个时候没有接收到有效的input, job会一直在等待中,你可以在例如job #1的output console中,点击这个input条件,提供input,构建才会继续。
下面解释input{…}里面支持写那些option。
参数说明:
一个完整的input,大概需要如下几个要点:
参数:message 必需的。 这将在用户提交 input 时作为说明信息呈现给用户。
参数:id input 的可选标识符, 默认为 stage 名称。
参数:ok 这个ok也是一个可选的option, 主要是在ok按钮上显示一些文本,在input表单里。
参数:submitter 这个submitter也是一个可选的option,里面可以写多个用户名称或者组名称,用逗号隔开。意思就是,只有这写名称的对应用户登陆jenkins,才能提交这个input动作,如果不写,默认是任何人都可以提交input。
参数:submitterParameter 环境变量的可选名称。如果存在,用 submitter 名称设置。
举例:
parameters 提示提交者提供的一个可选的参数列表,结合好了,会有非常多的妙用。
这里简单创建一个项目,用于一种思路的引导:
pipeline{
agent any
environment{
approvalMap = ''
}
stages {
stage('pre deploy'){
steps{
script{
approvalMap = input (
message: '准备发布到哪个环境?',
ok: '确定',
parameters:[
choice(name: 'ENV',choices: 'test\npre\nprod',description: '发布到什么环境?'),
string(name: 'myparam',defaultValue: '',description: '')
],
submitter: 'admin',
submitterParameter: 'APPROVER'
)
}
}
}
stage('deploy'){
steps{
echo "操作者是 ${approvalMap['APPROVER']}"
echo "发布到什么环境 ${approvalMap['ENV']}"
echo "自定义参数 ${approvalMap['myparam']}"
}
}
}
}
点击构建,程序将会在input的步骤停住,等待用户进行相应输入,从而进行不同构建,当然,这里的多环境只是做了一个简单的打印,如果再结合上判断,以及不同分支构建,就能实现更加丰富的功能,不用着急,很快就会介绍Jenkinsfile中的判断了。
注意:开头环境变量,先创建了一个空的名称,后边再将定义的参数结果赋值给开头的变量,这样便于后边调用,调用时直接引用这个Map类型即可。另外,因为这种赋值的方式属于Groovy语言的赋值方式,因此对应的赋值过程需要放在script块中。
3.7 when
指令说明:when指令允许Pipeline根据给定的条件确定是否执行该阶段。该when指令必须至少包含一个条件。如果when指令包含多个条件,则所有子条件必须为stage执行返回true。这与子条件嵌套在一个allOf条件中相同(见下面的例子)。
更复杂的条件结构可使用嵌套条件建:not,allOf或anyOf。嵌套条件可以嵌套到任意深度。
可选条件:
- branch :判断分支名称是否符合预期
用法:when { branch 'master' } - environment : 判断环境变量是否符合预期
用法:when { environment name: 'DEPLOY_TO', value: 'production' } - expression:判断表达式是否符合预期
用法:when { expression { return params.DEBUG_BUILD } } - not : 判断条件是否为假
用法:when { not { branch 'master' } } - allOf:判断所有条件是不是都为真
用法:when { allOf { branch 'master'; environment name: 'DEPLOY_TO', value: 'production' } } - anyOf:判断是否有一个条件为真
用法:when { anyOf { branch 'master'; branch 'staging' } } - beforeAgent:正常情况下,程序都是自上而下执行的,也就是在agent之后才会执行when,但是某些场景中,可能我们需要先做一下判断,然后再进入到agent字段中的,那么这个时候,就需要用到beforeAgent。
用法:when {beforeAgent true }
特别的:如果我们想要在进入agent之前进行判断,需要将beforeAgent设置为true
示例:
pipeline {
agent none
stages {
stage('Example Build') {
steps {
echo 'Hello World'
}
}
stage('Example Deploy') {
agent {
label "some-label"
}
when {
beforeAgent true //设置先对条件进行判断,符合预期才进入steps
branch 'production'
}
steps {
echo 'Deploying'
}
}
}
}
3.8 parallel并行执行
指令说明:Declarative Pipeline近期新增了对并行嵌套stage的支持,对耗时长,相互不存在依赖的stage可以使用此方式提升运行效率。除了parallel stage,单个parallel里的多个step也可以使用并行的方式运行,但是需要注意以下几点
- 一个stage只能有一个steps或者parallel
- 嵌套的stages里不能使用parallel
- parallel不能包含agent或者tools
- 通过设置failFast 为true表示:并行的job中如果其中的一个失败,则终止其他并行的stage
示例:
pipeline {
agent any
stages {
stage('Non-Parallel Stage') {
steps {
echo 'Non-parallel'
}
}
stage('Parallel Stage') {
agent any
failFast true
parallel {
stage('parallel 1') {
agent any
steps {
echo "parallel 1"
}
}
stage('parallel 2') {
steps {
echo "parallel 2"
}
}
}
}
}
}
3.9 Script{}--groovy脚本
指令说明:在声明式的pipeline中默认无法使用脚本语法,但是pipeline提供了一个脚本环境入口:script{},通过使用script来包裹脚本语句,即可使用脚本语法,script{}中不仅可以写脚本,同时也可以用直接用各种指令。
3.9.1条件处理-IF/ELSE
pipeline {
agent any
stages {
stage('stage 1') {
steps {
script{
if ( "1" =="1" ) {
echo "lalala"
}else {
echo "oooo"
}
}
}
}
}
3.9.2 for循环
pipeline{
agent{
label 'master'
}
stages{
stage('步骤1'){
steps{
script{
def list=['a','b','c']
for(i in list){
echo i
}
}
}
}
}
}
3.9.3异常处理-try/catch/finally
pipeline{
agent any
stages{
stage('步骤1'){
steps{
script{
try {
sh 'exit 1'
}
catch (exc) {
echo 'Something failed, I should sound the klaxons!'
}
finally{
echo 'this must be excuete'
}
}
}
}
}
}
3.9.4超时处理-timeout
pipeline{
agent any
stages{
stage("init") {
steps{
script {
timeout(1) {
echo ‘hell world!’
//sleep 61
}
}
}
}
}
}
备注:上面我没有执行sleep语句,那么这个打印hell world!的代码肯定能在一分钟之内完成,这个job执行的状态是成功。那么,如果我取消sleep这个前面注释,也就是这个代码要执行61秒以上的时间,但是我给了timeout是1分钟,那么这个job跑起来就会自动cancel,状态是aborted。
说明:time:整型,休眠时间。
unit(可选):时间单位,支持的值有NANOSECONDS、MICROSECONDS、MILLISECONDS、SECONDS、MINUTES(默认)、HOURS、DAYS。
3.9.5文件读写操作
script{
write_file_path = "D:\\CI\\testdata\\write.txt" #其他类型文件基本一样
file_contents = "Hello Anthony!! 这是一个测试例子"
writeFile file: write_file_path, text: file_contents
fileContents = readFile file: write_file_path
println fileContents
}
3.9.6定义字符串、数组、map字典
pipeline {
agent any
stages {
stage('Example') {
steps {
echo 'Hello World'
script {
def a=1
def b='hello wold'
def browsers = ['chrome', 'firefox']
def dics= [red: '#FF0000', green: '#00FF00', blue: '#0000FF']
echo '变量 a=='+a
echo '变量 b=='+b
echo "变量 dics第一个值是==${dics['red']}"
assert dics.blue == '#0000FF'
for (int i = 0; i < browsers.size(); ++i) {
echo "Testing the ${browsers[i]} browser"
}
}
}
}
}
}
3.9.7定义字函数方法
def fun(){
print 'this is first function'
}
pipeline {
agent any
stages {
stage('Example') {
steps {
echo 'Hello World'
script {
fun()
}
}
}
}
}
***文件目录相关步骤
3.10 deleteDir
删除当前目录,它是一个无参步骤,删除的是当前工作目录。通常它与dir步骤一起使用,用于删除指定目录下的内容。
3.11 dir
切换到目录。默认pipeline工作在工作空间目录下,dir步骤可以让我们切换到其它目录。例如:dir("/var/logs") { deleteDir() }
3.12 fileExists
判断文件是否存在。fileExists('/tmp/a.jar')判断/tmp/a.jar文件是否存在。如果参数是相对路径,则判断在相对当前工作目录下,该文件是否存在。结果返回布尔类型。
3.13 isUnix
判断是否为类Unix系统。如果当前pipeline运行在一个类Unix系统上,则返回true。
3.14 Pwd
确认当前目录。pwd与Linux的pwd命令一样,返回当前所在目录。它有一个布尔类型的可选参数:tmp,如果参数值为true,则返回与当前工作空间关联的临时目录。
3.15 writeFile
将内容写入指定文件中。
writeFile支持的参数有:
- file:文件路径,可以是绝对路径,也可以是相对路径。
- text:要写入的文件内容。
- encoding(可选):目标文件的编码。如果留空,则使用操作系统默认的编码。如果写的是Base64的数据,则可以使用Base64编码。
3.16 readFile
读取指定文件的内容,以文本返回。
readFile支持的参数有:
- file:路径,可以是绝对路径,也可以是相对路径。
- encoding(可选):读取文件时使用的编码。
import hudson.model.*;
pipeline{
agent any
stages{
stage('步骤1'){
steps{
dir('E:\\Devops_local'){
writeFile encoding: 'utf-8', file: 'test.txt', text: 'pipeline 读写练习'
script{
content = readFile encoding: 'utf-8', file: 'test.txt'
}
}
echo content
}
}
}
}
***制品相关步骤
3.17 Stash/Unstash
保存临时文件。
stash步骤可以将一些文件保存起来,以便被同一次构建的其他步骤或阶段使用。如果整个pipeline的所有阶段在同一台机器上执行,则stash步骤是多余的。所以,通常需要stash的文件都是要跨Jenkins node使用的。
stash步骤会将文件存储在tar文件中,对于大文件的stash操作将会消耗Jenkins master的计算资源。Jenkins官方文档推荐,当文件大小为5∼100MB时,应该考虑使用其他替代方案。
stash步骤的参数列表如下:
- name:字符串类型,保存文件的集合的唯一标识。
- allowEmpty:布尔类型,允许stash内容为空。
- excludes:字符串类型,将哪些文件排除。如果排除多个文件,则使用逗号分隔。留空代表不排除任何文件。
- includes:字符串类型,stash哪些文件,留空代表当前文件夹下的所有文件。
- useDefaultExcludes:布尔类型,如果为true,则代表使用Ant风格路径默认排除文件列表。
除了name参数,其他参数都是可选的。excludes和includes使用的是Ant风格路径表达式。
Unstash
取出之前stash的文件。
unstash步骤只有一个name参数,即stash时的唯一标识。通常stash与unstash步骤同时使用。以下是完整示例。
pipeline {
agent none
stages {
stage('stash') {
agent { label "master" }
steps {
script {
writeFile file: "a.txt", text: "$BUILD_NUMBER"
stash(name: "abc", include: "a.txt")
}
}
}
stage("unstash") {
agent { label "node2" }
steps {
script {
unstash("abc")
def content = readFile("a.txt")
echo "${content}"
}
}
}
}
}
stash步骤在master节点上执行,而unstash步骤在node2节点上执行。
***命令相关步骤
与命令相关的步骤其实是Pipeline:Nodes and Processes插件提供的步骤。由于它是Pipeline插件的一个组件,所以基本不需要单独安装。
3.18 Sh-执行shell命令
执行shell命令。
sh步骤支持的参数有:
- script:将要执行的shell脚本,通常在类UNIX系统上可以是多行脚本。
- encoding:脚本执行后输出日志的编码,默认值为脚本运行所在系统的编码。
- returnStatus:布尔类型,默认脚本返回的是状态码,如果是一个非零的状态码,则会引发pipeline执行失败。如果returnStatus参数为true,则不论状态码是什么,pipeline的执行都不会受影响。
- returnStdout:布尔类型,如果为true,则任务的标准输出将作为步骤的返回值,而不是打印到构建日志中(如果有错误,则依然会打印到日志中)。除了script参数,其他参数都是可选的。
returnStatus与returnStdout参数一般不会同时使用,因为返回值只能有一个。如果同时使用,则只有returnStatus参数生效。
3.19 bat/powershell
bat步骤执行的是Windows的批处理命令。powershell步骤执行的是PowerShell脚本,支持3+版本。这两个步骤支持的参数与sh步骤的一样。
***其他步骤
3.20 Error
主动报错,中止当前pipeline。
error 步骤的执行类似于抛出一个异常。它只有一个必需参数:message。通常省略参数:error("there's an error")。
3.21 Timeout
代码块超时时间。
为timeout步骤闭包内运行的代码设置超时时间限制。如果超时,将抛出一个org.jenkinsci.plugins.workflow.steps.FlowInterruptedException异常。timeout步骤支持如下参数:
- time:整型,超时时间。
- unit(可选):时间单位,支持的值有NANOSECONDS、MICROSECONDS、MILLISECONDS、SECONDS、MINUTES(默认)、HOURS、DAYS。
- activity(可选):布尔类型,如果值为true,则只有当日志没有活动后,才真正算作超时。
3.22 waitUntil
等待条件满足。
不断重复waitUntil块内的代码,直到条件为true。waitUntil不负责处理块内代码的异常,遇到异常时直接向外抛出。waitUntil步骤最好与timeout步骤共同使用,避免死循环。示例如下:
timeout(50) {
waitUntil {
script {
def r = sh script: 'curl http://example', returnStatus: true
retturn (r == 0)
}
}
}
3.23 Retry
重复执行块
执行N 次闭包内的脚本。如果其中某次执行抛出异常,则只中止本次执行,并不会中止整个retry的执行。同时,在执行retry的过程中,用户是无法中止pipeline的。
steps {
retry(20) {
script {
sh script: 'curl http://example', returnStatus: true
}
}
}
3.24 Sleep
让pipeline休眠一段时间。
sleep步骤可用于简单地暂停pipeline,其支持的参数有:
- time:整型,休眠时间。
- unit(可选):时间单位,支持的值有NANOSECONDS、MICROSECONDS、MILLISECONDS、SECONDS(默认)、MINUTES、HOURS、DAYS。
- 例子:
sleep 1
或
sleep time: 1, unit: 'MINUTES'
或
sleep(time: 1, unit: 'SECONDS')
小贴士
- Jenkins提供了一个pipeline代码片段生成器,通过界面操作就可以生成代码。(只有pipeline项目有“Pipeline Syntax菜单”)
- VS Code扩展:Jenkins Pipeline Linter Connector,支持对Jenkinsfile的语法检验。
- 使用Workspace Cleanup插件清理空间。
- Ant风格路径表达式。
Apache Ant样式的路径有三种通配符匹配方法,利用它们可以组合出多种路径模式:
Wildcard | Description |
? | 匹配任意单字符 |
* | 匹配0或者任意数量的字符,不包含/ |
** | 匹配0或者更多数量的目录,不包含/ |
Ant风格路径匹配实例:
Path | Description |
/app/*.x | 匹配(Matches)app路径下所有.x文件 |
/app/p?ttern | 匹配(Matches) /app/pattern 和 /app/pXttern,但是不包括/app/pttern |
/**/example | 匹配项目根路径下 /project/example, /project/foow/example, 和 /example |
/app/**/dir/file. | 匹配(Matches) /app/dir/file.jsp, /app/foo/dir/file.html,/app/foo/bar/dir/file.pdf, 和 /app/dir/file.java |
/**/*.jsp | 匹配项目根路径下任何的.jsp 文件 |
需要注意的是,路径匹配遵循最长匹配原则(has more characters),例如/app/dir/file.jsp符合/**/*.jsp和/app/dir/*.jsp两个路径模式,那么最终就是根据后者来匹配。
参考文档:https://blog.51cto.com/ygqygq2/2446145