Jenkins系列之pipeline语法介绍与案例

Jenkins Pipeline 的核心概念:

  • Pipeline 是一套运行于 Jenkins上的 工作流框架,将原本独立运行于单个或者多个节点的任务连接起来,实现单个任务难以完成的复杂流程编排与可视化。
  • Pipeline_是 _Jenkins2.X最核心的特性,帮助 Jenkins 实现从CI到CD与DevOps的转变。
  • _Pipeline_是一组插件,让 Jenkins可以实现 *持续交付管道的落地和实施。

持续交付管道(CD Pipeline)是将软件从版本控制阶段到交付给用户或客户的完整过程的自动化表现。软件的每一次更改(提交到源代码管理系统)都要经过一个复杂的过程才能被发布。

Pipeline_提供了一组可扩展的工具,通过 _Pipeline Domain Specific Language(DSL)syntax_可以达到 _Pipeline as Code(Jenkinsfile存储在项目的源代码库)的目的。

Pipeline入门:

先决条件
要使用Jenkins Pipeline,您将需要:

  • Jenkins 2.x或更高版本
  • Pipeline插件(请自行在插件管理中安装。)

_Pipeline_支持两种语法:

  • Declarative 声明式
  • Scripted pipeline 脚本式

    Jenkins系列之pipeline语法介绍与案例
  • 直接在Jenkins网页界面中输入脚本。

  • 通过创建一个Jenkinsfile可以检入项目的源代码管理库。

用任一方法定义Pipeline的语法是一样的,但是Jenkins支持直接进入Web UI的Pipeline,通常认为最佳实践是在Jenkinsfile Jenkins中直接从源代码控制中加载Pipeline。

要在 Jenkins Web UI_中创建基本 _Pipeline

  • Stages:阶段组/Stage:阶段
  • 一个 Pipeline 有多个 Stage 组成,每个 Stage 包含一组 Step。
  • 注意一个 Stage 可以跨多个 Node 执行,即 Stage 实际上是 Step 的逻辑分组。
  • 一个Jenkinsfile 可以分为大的阶段,如打包、构建、 部署。测试
  • 构建的流程,可以分为这几步,获取源代码,然后打包,构建,进行编译,替换配置文件,编译完打包,进行部署 这个阶段就是stage
  • Node:节点,一个Node就是一个Jenkins节点,或者是Master,或者是Agent,是执行Step的具体运行环境。
  • Steps:步骤,Step是最基本的操作单元,小到创建一个目录,大到构建一个Docker镜像,由各类Jenklins Plugin提供,例如:sh ‘make’

  • 块(blocks{}):
    由大括号括起来的语句,如pipeline{},Section{},parameters{},script{}

  • 章节(Sections):
    通常包含一个或多个指令或步骤。如 agent 、post、stages、steps
  • 指令(Directives):
    environment、options、parameters、triggers(触发)、stage、tools、when
  • 步骤(Steps):
    执行脚本式pipeline:在该语句块内使用script{}
  • agent
    必须存在,agent必须在pipeline块内的顶层定义,但stage内是否使用是可选的
    参数:any/none/label/node/docker/dockerfile
    常用选项 label/cuetomWorkspace/reuseNode

指令名 说明 作用域 agent 定义执行任务的代理 stage 或pipeline input 暂停pipeline,提示输入内容 stage environment 设置环境变量 stage或pipeline tools 自动下载并安装指定的工具,并将其加入到PATH变量中 stage或pipeline options 配置Jenkins pipeline本身,如options{retry(3}},指pipeline失败时再重试2次 stage 或 pipeline build 触发其他的job steps when 定义阶段执行的条件 stage triggers 定义执行pipeline的触发器 pipeline parameters 执行pipeline前传入一些参数 pipeline parallel 并行执行多个step stage

示例:

  • agent:
agent { label 'my-label' }

agent {
    node {
        label 'my-label'
        customWorkspace '/some/other/path'
    }
}

agent {
    docker {
        image 'application_name:verison'
        label 'my-label'
        args '-v /tmp:/tmp'
    }
}
  • stage间通过stash进行文件共享,即使stage不在同一个执行主机上:
pipeline{
    agent none
    stages{
        stage('stash'){
            agent { label "master" }
            steps{
                writeFile file: "a.txt", text: "$BUILD_NUMBER"
                stash name: "abc", includes: "a.txt"
            }
        }
        stage('unstash'){
            agent { label "node" }
            steps{
                script{
                    unstash("abc")
                    def content = readFile("a.txt")
                    echo "${content}"
                }
            }
        }
    }
}
  • steps中的一些操作:命令名 说明 error 抛出异常,中断整个pipeline timeout timeout闭包内运行的步骤超时时间 waitUntil 一直循环运行闭包内容,直到return true,经常与timeout同时使用 retry 闭包内脚本重复执行次数 sleep 暂停pipeline一段时间,单位为秒
pipeline{
    agent any
    stages{
        stage('stash'){
            steps{
                timeout(50){
                    waitUntil{
                        script{
                            def r = sh script: 'curl http://xxx', returnStatus: true
                            return (r == 0)
                        }
                    }
                }
                retry(10){
                    script{
                        sh script: 'curl http://xxx', returnStatus: true
                    }
                }
                sleep(20)
            }
        }
    }
}
  • triggers:定时构建
pipeline {
  agent any
  triggers {
      cron('H 9 * * *')
    }
}
  • paramparameters:参数化构建
  • pipeline 脚本
pipeline {
    agent any
    parameters {
      choice(name: 'ENV', choices: 'dev\nsit\nuat', description: '环境')
      // 或者 choice(name: 'ENV', choices: ['dev','sit',uat'], description: '环境')
      string(name: 'PROJECT', defaultValue: 'example-demo', description: '项目')
      booleanParam(defaultValue: true, description: '', name: 'BOOLEAN')
      text(defaultValue: '''this is a multi-line
                            string parameter example
                            ''', name: 'MULTI-LINE-STRING')
    }
    stages {
        stage('Hello') {
            steps {
                echo 'Hello World'
            }
        }
    }
}

  1. web_ui配置:
    Jenkins系列之pipeline语法介绍与案例
    也可用于选择git分支/tag 进行发布
    1. 添加参数类型为:
      Jenkins系列之pipeline语法介绍与案例
    2. 编写groovy脚本:
      替换掉自己的git项目地址!
def gettags = ("git ls-remote --heads  --tags ssh://git@{ your ip }/xx/project_name.git").execute()
if (ENV.equals("pre")){
  gettags = ("git ls-remote --heads  --tags ssh://git@{ your ip }/xx/project_name.git").execute()
}
def repoNameList = gettags.text.readLines().collect {
    it.split()[1].replaceAll('refs/heads/', '').replaceAll('refs/tags/', '').replaceAll("\\^\\{\\}", '')
}
repoNameList.eachWithIndex { it, i ->
  if (it.equals("master")){
    repoNameList[i]= "master:selected"
 }
}
return repoNameList

Jenkins系列之pipeline语法介绍与案例
Jenkins系列之pipeline语法介绍与案例 效果:
Jenkins系列之pipeline语法介绍与案例
* post:后置操作
Jenkinsfile (Declarative Pipeline)
pipeline {
    agent any
    stages {
        stage('Hello') {
            steps {
                sh 'ls'
            }
            post {
                always {
                  echo '步骤Hello体里的post操作'
                }
            }
        }
    }
    // post部分可以同时包含多种条件块。
    post {
        always {
            echo '永远都会执行'
        }
        success {
            echo '本次构建成功时执行'
        }
        unstable {
            echo '构建状态为不稳定时执行。'
        }
        failure {
            echo '本次构建失败时执行'
        }
        changed {
            echo '只要本次构建状态与上一次构建状态不同就执行。'
        }
        fixed {
            echo '上一次构建状态为失败或不稳定,当前完成状态为成功时执行。'
        }
        regression {
            echo '上一次构建状态为成功,当前构建状态为失败、不稳定或中止时执行。'
        }
        aborted {
            echo '当前执行结果是中止状态时(一般为人为中止)执行。'
        }
        cleanup {
            echo '清理条件块。不论当前完成状态是什么,在其他所有条件块执行完成后都执行'}
    }
}

效果:

Jenkins系列之pipeline语法介绍与案例
  • 执行自动化测试脚本并通过飞书卡片消息发送执行结果到飞书群:
    先上效果图:
    Jenkins系列之pipeline语法介绍与案例
    图中用例执行结果需在代码中获取pytest执行结果统计
    需在最外层conftest中加以下代码:
from _pytest import terminal

def pytest_terminal_summary(terminalreporter):
    """收集测试结果,注:跟xdist插件不兼容"""
    # print(terminalreporter.stats)
    total = terminalreporter._numcollected - len(terminalreporter.stats.get('deselected', []))  # 收集总数-未选中用例数
    passed = len([i for i in terminalreporter.stats.get('passed', []) if i.when == 'call'])
    failed = len([i for i in terminalreporter.stats.get('failed', []) if i.when == 'call'])
    error = len([i for i in terminalreporter.stats.get('error', []) if i.when != 'teardown'])
    skipped = len([i for i in terminalreporter.stats.get('skipped', []) if i.when != 'teardown'])
    pass_rate = round(passed / (total - skipped) * 100, 2)

    # terminalreporter._sessionstarttime 会话开始时间
    duration = time.time() - terminalreporter._sessionstarttime
    # 将结果写入到一个文件中,后续再读取出来
    result_path = os.path.join(PROJECT_DIR, "reports/result.json")
    with open(result_path, "w")as fp:
        fp.write(
            str({"total": total, "passed": passed, "failed": failed, "error": error, "skipped": skipped,
                 "pass_rate": pass_rate, "duration": round(duration, 3)}))

如何发送卡片消息到飞书群(企微/钉钉同理):

Original: https://www.cnblogs.com/micheryu/p/15917059.html
Author: 网名余先生
Title: Jenkins系列之pipeline语法介绍与案例

原创文章受到原创版权保护。转载请注明出处:https://www.johngo689.com/116712/

转载文章受原作者版权保护。转载请注明原作者出处!

(0)

大家都在看

免费咨询
免费咨询
扫码关注
扫码关注
联系站长

站长Johngo!

大数据和算法重度研究者!

持续产出大数据、算法、LeetCode干货,以及业界好资源!

2022012703491714

微信来撩,免费咨询:xiaozhu_tec

分享本页
返回顶部