Jenkinsfile生成器技能
生成遵循最佳实践的生产就绪Jenkinsfile。所有生成的文件都使用devops-skills:jenkinsfile-validator技能进行验证。
何时使用
- 创建新的Jenkinsfile(声明式或脚本式)
- CI/CD管道,Docker/Kubernetes部署
- 并行执行,矩阵构建,参数化管道
- DevSecOps管道与安全扫描
- 共享库脚手架
快速参考
// 最小声明式管道
pipeline {
agent any
stages {
stage('Build') { steps { sh 'make' } }
stage('Test') { steps { sh 'make test' } }
}
}
// 容错阶段
stage('Flaky Tests') {
steps {
catchError(buildResult: 'SUCCESS', stageResult: 'UNSTABLE') {
sh 'run-flaky-tests.sh'
}
}
}
// 条件部署与审批
stage('Deploy') {
when { branch 'main'; beforeAgent true }
input { message 'Deploy to production?' }
steps { sh './deploy.sh' }
}
| 选项 | 目的 |
|---|---|
timeout(time: 1, unit: 'HOURS') |
防止挂起构建 |
buildDiscarder(logRotator(numToKeepStr: '10')) |
管理磁盘空间 |
disableConcurrentBuilds() |
防止竞态条件 |
catchError(buildResult: 'SUCCESS', stageResult: 'FAILURE') |
继续出错 |
核心能力
1. 声明式管道(推荐)
流程:
- 读取模板以供结构参考:
- 阅读
assets/templates/declarative/basic.Jenkinsfile以了解标准结构 - 模板显示预期的节:pipeline → agent → environment → options → parameters → stages → post
- 对于复杂请求,适应结构而不是照搬
- 阅读
- 查阅参考文档:
- 阅读
references/best_practices.md以了解性能,安全性和可靠性模式 - 阅读
references/common_plugins.md以了解插件特定语法
- 阅读
- 生成所需元素:
- 适当的阶段,具有描述性名称
- 环境块与凭据绑定(永远不要硬编码秘密)
- 选项:超时,buildDiscarder,时间戳,disableConcurrentBuilds
- 后期条件:始终(清理),成功(工件),失败(通知)
- 始终在并行块中添加
failFast true或parallelsAlwaysFailFast() - 使用
archiveArtifacts时始终包含fingerprint: true
- 始终使用devops-skills:jenkinsfile-validator技能进行验证
2. 脚本式管道
何时: 复杂的条件逻辑,动态生成,完整的Groovy控制 流程:
- 读取模板以供结构参考:
- 阅读
assets/templates/scripted/basic.Jenkinsfile以了解node/stage模式 - 了解try-catch-finally结构以处理错误
- 阅读
- 实现try-catch-finally以处理错误
- 始终使用devops-skills:jenkinsfile-validator技能进行验证
3. 并行/矩阵管道
使用parallel {}块或matrix {}与axes {}进行多维构建。
4. 安全扫描(DevSecOps)
添加SonarQube,OWASP Dependency-Check,Trivy阶段与失败阈值。
5. 共享库脚手架
python3 scripts/generate_shared_library.py --name my-library --package org.example
声明式语法参考
代理类型
agent any // 任何可用代理
agent { label 'linux && docker' } // 基于标签
agent { docker { image 'maven:3.9.11-eclipse-temurin-21' } }
agent { kubernetes { yaml '...' } } // K8s pod模板
agent { kubernetes { yamlFile 'pod.yaml' } } // 外部YAML
环境与凭据
environment {
VERSION = '1.0.0'
AWS_KEY = credentials('aws-key-id') // 创建_USR和_PSW变量
}
选项
options {
buildDiscarder(logRotator(numToKeepStr: '10'))
timeout(time: 1, unit: 'HOURS')
disableConcurrentBuilds()
timestamps()
parallelsAlwaysFailFast()
durabilityHint('PERFORMANCE_OPTIMIZED') // 2-6倍速度提升,适用于简单管道
}
参数
parameters {
string(name: 'VERSION', defaultValue: '1.0.0')
choice(name: 'ENV', choices: ['dev', 'staging', 'prod'])
booleanParam(name: 'SKIP_TESTS', defaultValue: false)
}
何时条件
| 条件 | 示例 |
|---|---|
branch |
branch 'main'或branch pattern: 'release/*', comparator: 'GLOB' |
tag |
tag pattern: 'v*', comparator: 'GLOB' |
changeRequest |
changeRequest target: 'main' |
changeset |
changeset 'src/**/*.java' |
expression |
expression { env.DEPLOY == 'true' } |
allOf/anyOf/not |
组合条件 |
如果条件失败,则添加beforeAgent true以跳过代理分配。
错误处理
catchError(buildResult: 'UNSTABLE', stageResult: 'FAILURE') { sh '...' }
warnError('msg') { sh '...' } // 标记UNSTABLE但继续
unstable(message: 'Coverage low') // 显式UNSTABLE
error('Config missing') // 失败无堆栈跟踪
后期部分
post {
always { junit '**/target/*.xml'; cleanWs() }
success { archiveArtifacts artifacts: '**/*.jar', fingerprint: true }
failure { slackSend color: 'danger', message: 'Build failed' }
fixed { echo 'Build fixed!' }
}
顺序: always → changed → fixed → regression → failure → success → unstable → cleanup
注意: 使用archiveArtifacts时始终使用fingerprint: true以进行构建可追溯性和工件跟踪。
并行与矩阵
重要: 始终确保并行块在第一次失败时快速失败,使用以下方法之一:
选项1:全局(推荐) - 在管道选项中使用parallelsAlwaysFailFast():
options {
parallelsAlwaysFailFast() // 适用于管道中的所有并行块
}
这是首选方法,因为它自动涵盖所有并行块。
选项2:每个块 - 在个别并行阶段使用failFast true:
stage('Tests') {
failFast true // 仅影响此并行块
parallel {
stage('Unit') { steps { sh 'npm test:unit' } }
stage('E2E') { steps { sh 'npm test:e2e' } }
}
}
注意: 如果在选项中设置了parallelsAlwaysFailFast(),则在个别并行块上显式使用failFast true是多余的。
stage('Matrix') {
failFast true
matrix {
axes {
axis { name 'PLATFORM'; values 'linux', 'windows' }
axis { name 'BROWSER'; values 'chrome', 'firefox' }
}
excludes { exclude { axis { name 'PLATFORM'; values 'linux' }; axis { name 'BROWSER'; values 'safari' } } }
stages { stage('Test') { steps { echo "Testing ${PLATFORM}/${BROWSER}" } } }
}
}
### 输入(手动审批)
```groovy
stage('Deploy') {
input { message 'Deploy?'; ok 'Deploy'; submitter 'admin,ops' }
steps { sh './deploy.sh' }
}
重要: 将input放在步骤之外以避免占用代理。
脚本式语法参考
node('agent-label') {
try {
stage('Build') { sh 'make build' }
stage('Test') { sh 'make test' }
} catch (Exception e) {
currentBuild.result = 'FAILURE'
throw e
} finally {
deleteDir()
}
}
// 并行
parallel(
'Unit': { node { sh 'npm test:unit' } },
'E2E': { node { sh 'npm test:e2e' } }
)
// 环境
withEnv(['VERSION=1.0.0']) { sh 'echo $VERSION' }
withCredentials([string(credentialsId: 'key', variable: 'KEY')]) { sh 'curl -H "Auth: $KEY" ...' }
@NonCPS用于非序列化操作
@NonCPS
def parseJson(String json) {
new groovy.json.JsonSlurper().parseText(json)
}
规则: @NonCPS内部无管道步骤(sh,echo)。用于JsonSlurper,迭代器,正则表达式匹配器。
Docker与Kubernetes
Docker代理
agent { docker { image 'maven:3.9.11'; args '-v $HOME/.m2:/root/.m2'; reuseNode true } }
构建与推送
def img = docker.build("myapp:${BUILD_NUMBER}")
docker.withRegistry('https://registry.example.com', 'creds') { img.push(); img.push('latest') }
Kubernetes Pod
agent {
kubernetes {
yaml '''
apiVersion: v1
kind: Pod
spec:
containers:
- name: maven
image: maven:3.9.11-eclipse-temurin-21
command: [sleep, 99d]
'''
}
}
// 使用:container('maven') { sh 'mvn package' }
共享库
@Library('my-shared-library') _
// 或动态:library 'my-library@1.0.0'
// vars/log.groovy
def info(msg) { echo "INFO: ${msg}" }
// 使用
log.info 'Starting build'
验证工作流
至关重要:始终使用devops-skills:jenkinsfile-validator技能进行验证:
- 生成Jenkinsfile
- 调用
devops-skills:jenkinsfile-validator技能 - 根据严重性处理验证结果:
- 错误: 在呈现给用户之前必须修复 - 这些破坏了管道
- 警告: 应该修复 - 这些表明潜在问题
- 信息/建议: 根据用例考虑应用:
- 并行块的
failFast true→ 默认应用 - 构建触发器 → 询问用户是否需要自动构建
- 其他优化 → 如果它们改善了管道,则应用
- 并行块的
- 修复后重新验证
- 仅向用户呈现经过验证的Jenkinsfile
验证命令:
# 完整验证(语法+安全性+最佳实践)
bash scripts/validate_jenkinsfile.sh Jenkinsfile
# 仅语法(最快)
bash scripts/validate_jenkinsfile.sh --syntax-only Jenkinsfile
生成器脚本
何时使用脚本与手动生成:
- 使用脚本用于: 具有常见模式的简单,标准管道(基本CI,直接CD)
- 使用手动生成用于: 具有多个功能(并行测试+安全扫描+Docker+K8s部署),自定义逻辑或非标准要求的复杂管道
# 声明式(简单管道)
python3 scripts/generate_declarative.py --output Jenkinsfile --stages build,test,deploy --agent docker
# 脚本式(简单管道)
python3 scripts/generate_scripted.py --output Jenkinsfile --stages build,test --agent label:linux
# 共享库(始终使用脚本进行脚手架)
python3 scripts/generate_shared_library.py --name my-library --package com.example
插件文档查找
始终咨询Context7或WebSearch:
- 未在
references/common_plugins.md中涵盖的插件 - 版本特定的文档请求
- 复杂的插件配置或高级选项
- 当用户明确要求最新文档时
可以跳过外部查找时:
- 使用已在
references/common_plugins.md中记录的基本插件语法 - 简单,文档良好的插件步骤(例如,基本
sh,checkout scm,junit)
在common_plugins.md中涵盖的插件: Git,Docker,Kubernetes,凭据,通知
查找方法(按优先级顺序):
- Context7:
mcp__context7__resolve-library-id带有/jenkinsci/<plugin-name>-plugin - WebSearch:
Jenkins [plugin-name] plugin documentation 2025 - 官方: plugins.jenkins.io,jenkins.io/doc/pipeline/steps/
参考
references/best_practices.md- 性能,安全性,可靠性模式references/common_plugins.md- Git,Docker,K8s,凭据,通知assets/templates/- 声明式和脚本式模板devops-skills:jenkinsfile-validator技能 - 语法和最佳实践验证
始终优先选择声明式,除非需要脚本灵活性。