当前位置: 首页 > 知识库问答 >
问题:

Jenkins pipelineJob DSL不解释管道脚本中的变量

尹昀
2023-03-14

我试图使用jobDSL插件中的pipelineJob函数生成Jenkins管道,但是无法将参数从DSL传递到管道脚本。我有几个项目使用本质上相同的Jenkinsfile,只是在几个步骤上有所不同。我正在尝试使用JobDSL插件动态生成这些管道,并解释其中我想要更改的值,以匹配DSL的参数。

我已经在管道脚本和DSL中尝试了几乎所有可能的字符串解释组合,但无法获得Jenkins /groovy来解释管道脚本中的变量。

我在管道步骤中调用作业 DSL:

def projectName = "myProject"
def envs = ['DEV','QA','UAT']
def repositoryURL = 'myrepo.com'

jobDsl targets: ['jobs/*.groovy'].join('\n'), 
    additionalParameters: [
        project: projectName, 
        environments: envs, 
        repository: repositoryURL
    ],
    removedJobAction: 'DELETE',
    removedViewAction: 'DELETE'

DSL如下:

pipelineJob("${project} pipeline") {
    displayName('Pipeline')
        definition {
            cps { 
                script(readFileFromWorkspace(pipeline.groovy))
            }
        }
    }

pipeline.groovy:

pipeline {
    agent any

    environment {
        REPO = repository
    }

    parameters {
        choice name: "ENVIRONMENT", choices: environments
    }

    stages {
        stage('Deploy') {
            steps {
                echo "Deploying ${env.REPO} to ${params.ENVIRONMENT}..."
            }
        }
    }
}

我在 additionalParameters 中传递的变量在 jobDSL 脚本中解释;确实会生成具有正确名称的管道。问题是变量没有传递给从工作区读取的管道脚本 - 生成的管道的 Jenkins 配置看起来与文件完全相同,没有对变量进行任何解释。

我做了很多尝试来解释这个字符串,包括很多“${environments}”、${environments}、$environments、$environments的变体...我找不到任何有用的。我还尝试将该文件作为gstringImpl读取:

script("${readFileFromWorkspace(pipeline.groovy)}")

有没有人对如何使变量向下传播到管道脚本有任何想法?我知道我可以使用 for 循环在脚本文本上执行 string.replaceAll(),但这似乎很麻烦;一定有更好的方法。

共有3个答案

吕自怡
2023-03-14

您可以通过在管道作业中定义环境变量,然后在管道中使用这些变量来实现您尝试执行的操作。

它们有点受限,因为环境变量是字符串,但是它应该对基本的东西起作用

前任。:

//job-dsl
pipelineJob('example') {
    environmentVariables {
        // these vars could be specified by parameters of this job
        env('repository', 'blah')
        env('environments', "a,b,c"]) //comma separated string
    }
    displayName('Pipeline')
        definition {
            cps { 
                script(readFileFromWorkspace(pipeline.groovy))
            }
        }
    }
}

然后在管道中:

//pipeline.groovy
pipeline {
    agent any

    environment {
        REPO = env.repository
    }

    parameters {
        choice name: "ENVIRONMENT", choices: env.environments.split(',') 
        //note the need to split the comma separated string above
    }
}
越扬
2023-03-14

您需要使用完整的作业名称作为不带引号的变量。例如,如果 JOBNAME 是包含整个作业名称的参数:

pipelineJob(JOBNAME) {
    displayName('Pipeline')
        definition {
            cps { 
                script(readFileFromWorkspace(pipeline.groovy))
            }
        }
    }
罗和煦
2023-03-14

我想出了一个办法来完成这项工作。这不是我想要的,这是在创建工作时隐式解释文件的字符串内容,但它确实有效;它只是增加了一步。

import groovy.text.SimpleTemplateEngine

def fileContents = readFileFromWorkspace "pipeline.groovy"

def engine = new SimpleTemplateEngine()
template = engine.createTemplate(fileContents).make(binding.getVariables()).toString()

pipelineJob("${project} pipeline") {
    displayName('Pipeline')
    definition {
        cps { 
            script(template)
        }
    }
}

这将从工作区中读取一个文件,然后将其用作带有绑定变量的模板。完成此工作所需的其他更改是转义Jenkinsfile脚本中使用的任何变量,如\${VARIABLE},以便在运行时展开这些变量,而不是在构建作业时展开。创建工作时要扩展的任何变量都应作为${VARIABLE}引用。

 类似资料:
  • 我在Ansible脚本模块解释with_items变量时遇到了问题。 vsa_deploy_config/tasks/main.yml: vsa_deploy_config/vars/main.yml: 当我运行行动手册时,我收到以下错误: 任务[vsa_deploy_config:在中心服务器上部署VSA]* * * * * * * * * * * * * * * * * * * * * * *

  • 我正在尝试使用groovy构建脚本将构建管道迁移到“管道插件”。 我的管道通常是: 测试(梯度) 我想在我的jenkins构建脚本中使用像version/group等的gradle变量来发布到artiFactory中的正确文件夹中。这是artiFactory插件过去会为我处理的事情。如何实现? 对于单个gradle项目,我使用如下内容:

  • 问题内容: 我正在研究如何在项目的scm中使用新的Jenkins Pipeline插件(我们使用GIT)。 作业脚本是从SCM加载的(“来自SCM的管道脚本”选项),并且在脚本中执行。 问题是提交是重复的。在build目录中,有2个具有相同的提交,因此change视图可能非常混乱: 在多分支管道中也会发生此问题。 这里是内容: 难道我做错了什么 ? Jenkins版本:1.642.2(docker

  • 问题内容: 有没有办法在Powershell脚本中使用Groovy变量?我的示例脚本如下。 问题答案: 您不能在单引号或三单引号中插入变量。使用三重双引号:

  • 我正在使用位于git存储库中的Jenkins文件。我已经使用来自scm的管道脚本配置了新作业,该脚本指向我的JenkinsFile。我试图在我的Jenkins file pipeline脚本中使用git模块,以便从我的git repo中提取我的数据,而不需要配置prestatic变量,并且仅仅使用在我的作业中已经配置的scm pipeline脚本下的存储库URL变量。在我的Jenkins管道脚本中

  • 问题内容: 我正在尝试使用groovy构建脚本将构建管道迁移到“ Pipeline插件”。 我的管道通常是: 测试(等级) IntegrationTest(等级) 构建(渐变) 发布(人工工厂) 我想在我的jenkins构建脚本中使用gradle变量,例如version / group等,以发布到工件中的正确文件夹。过去,人工插件会为我解决。如何做到这一点? 对于单个gradle项目,我使用如下代