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

Jenkins中Groovy DSL管道中bat函数的返回值

云昊阳
2023-03-14

我在Jenkins中写了一个Groovy DSL声明性管道脚本。该脚本在运行在Windows Server 2012上的从代理上执行。在这个代理机器上有一个命令行可执行文件,叫做Kitchen。我使用Groovy的bat()方法执行Kitchen程序,并输入在构建时传递到管道中的参数。

该脚本很简单,分两个阶段执行以下操作

  1. 接受一个AWARD_YEAR参数
  2. 从SVN签出一个项目
  3. 通过一个bat()函数执行Kitchen程序

我用的是Jenkins 2.235.3

kitchen可执行文件返回0-9范围内的退出代码。当退出代码不是0时,这表示可执行文件失败。但是,目前的情况是,不管退出代码如何,管道执行始终成功。为了解决这个问题,我需要将退出代码存储在一个变量中,然后检查它的值。

然而,当我试图将结果存储到变量中时,我得到如下所示的错误。

下面是导致错误的代码

pipeline {
    agent { label 'pentaho-test' }


    parameters {
        string(name: 'AWARD_YEAR', defaultValue: "${Calendar.getInstance().get(Calendar.YEAR)}", description: 'Award Year Parameter')
    }
    
    stages {
        stage('Checkout') {
            steps {
                checkout changelog: false, poll: false, scm: [
                        $class: 'SubversionSCM', 
                        additionalCredentials: [], 
                        excludedCommitMessages: '', 
                        excludedRegions: '', 
                        excludedRevprop: '', 
                        excludedUsers: '', 
                        filterChangelog: false, 
                        ignoreDirPropChanges: false, 
                        includedRegions: '', 
                        locations: [[cancelProcessOnExternalsFail: true, 
                            credentialsId: 'hudson', 
                            depthOption: 'infinity', 
                            ignoreExternalsOption: true, 
                            local: '.', 
                            remote: 'https://svn.int.domain.edu/project/trunk']], 
                        quietOperation: true, 
                        workspaceUpdater: [$class: 'UpdateUpdater']
                ]
            }
        }
        stage('Run Kitchen') {       
            steps {
                def result = bat( label: '', returnStdout: true, script: 'kitchen -args %AWARD_YEAR%'  )
                
                echo result     
            }

        }

    }

}

以下是Jenkins控制台中显示的错误

org.codehaus.groovy.control.MultipleCompilationErrorsException: startup failed:
WorkflowScript: 35: Expected a step @ line 35, column 5.
                result = bat( label: '', returnStdout: true, script: 'kitchen -args %AWARD_YEAR%'  )
       ^

1 error

    at org.codehaus.groovy.control.ErrorCollector.failIfErrors(ErrorCollector.java:310)
    at org.codehaus.groovy.control.CompilationUnit.applyToPrimaryClassNodes(CompilationUnit.java:1085)
    at org.codehaus.groovy.control.CompilationUnit.doPhaseOperation(CompilationUnit.java:603)
    at org.codehaus.groovy.control.CompilationUnit.processPhaseOperations(CompilationUnit.java:581)
    at org.codehaus.groovy.control.CompilationUnit.compile(CompilationUnit.java:558)
    at groovy.lang.GroovyClassLoader.doParseClass(GroovyClassLoader.java:298)
    at groovy.lang.GroovyClassLoader.parseClass(GroovyClassLoader.java:268)
    at groovy.lang.GroovyShell.parseClass(GroovyShell.java:688)
    at groovy.lang.GroovyShell.parse(GroovyShell.java:700)
    at org.jenkinsci.plugins.workflow.cps.CpsGroovyShell.doParse(CpsGroovyShell.java:142)
    at org.jenkinsci.plugins.workflow.cps.CpsGroovyShell.reparse(CpsGroovyShell.java:127)
    at org.jenkinsci.plugins.workflow.cps.CpsFlowExecution.parseScript(CpsFlowExecution.java:561)
    at org.jenkinsci.plugins.workflow.cps.CpsFlowExecution.start(CpsFlowExecution.java:522)
    at org.jenkinsci.plugins.workflow.job.WorkflowRun.run(WorkflowRun.java:337)
    at hudson.model.ResourceController.execute(ResourceController.java:97)
    at hudson.model.Executor.run(Executor.java:428)
Finished: FAILURE

当我按照以下步骤修改脚本时,脚本会无错误地执行,但退出代码不会存储,因此即使二进制可执行文件失败,管道也会显示为成功。

steps {
     result = bat label: '', returnStdout: true, script: 'kitchen -args %AWARD_YEAR%'  
}

还有另外两个StackOverflow问题会问这个特定的问题,但是这个解决方案会导致我收到的错误。

共有1个答案

郝昊东
2023-03-14

如果要从sh步骤捕获结果并将其分配给变量,则需要在脚本块中执行此操作。

改变

stage('Run Kitchen') {       
    steps {
        def result = bat( label: '', returnStdout: true, script: 'kitchen -args %AWARD_YEAR%'  )
                
        echo result     
    }
}

stage('Run Kitchen') {       
    steps {
        script {
            def result = bat( label: '', returnStdout: true, script: 'kitchen -args %AWARD_YEAR%'  )
                
            echo result     
        }
    }
 }

你应该解决你现在看到的问题。

 类似资料:
  • 问题内容: 我正在尝试为jenkins groovy脚本获取分支的名称。我无法获取当前的分支名称。我尝试以下方法: 这是输出-它始终返回null。 我想念什么吗? 问题答案: 此变量仅在多分支管线中起作用: BRANCH_NAME对于多分支项目,此名称将设置为正在构建的分支的名称,例如,如果您希望从主分支而不是功能分支部署到生产中。 我在正常的管道中进行测试

  • 问题内容: 我的jenkinsfile中有一个执行bat命令的阶段: 我的批处理命令需要一个参数,该参数是svn中的当前分支。 当我使用这个: 回声“ SVN_BRANCH_NAME是$ {env.BRANCH_NAME}” 它会给出BRANCH_NAME的值,但是如果我将其作为参数传递给我的批处理文件,它将按字面意义传递$ {env.BRANCH_NAME}而不是该值。 他们有办法吗? 问题答案

  • 我正在使用一个bash脚本,我想执行一个函数来打印返回值: 当我执行时,它不会打印“34”。为什么会这样呢?

  • 有没有可能创建一个函数,它将lambda函数作为参数(每个lambda函数使用参数),然后返回一个具有单个参数的新函数,并返回所有lambda函数的乘积? 以下是我的非工作示例: 所以本质上,你有一个函数,它需要4个lambda函数,每个函数使用参数。例如,的参数可以类似于。 然后返回一个名为的新函数,该函数的输出是所有lambda函数的乘积,并且有一个参数,该参数传递到的每个lambda函数的参

  • 问题内容: 我在从Node.js中的回调函数返回值时遇到了小麻烦,我将尝试尽可能轻松地解释我的情况。考虑一下我有一个片段,它包含URL,并命中该URL,并提供输出: 我试图将其包装在函数中并返回如下值: 因为在我的Node.js代码中,我有很多语句将决定value的值,例如: 关键是a内的所有语句将保持相同,除了的值。因此,绝对需要将这些通用代码放入函数中。我尝试了同样的方法,但是in总是会回报我

  • 我正在学习指针是如何工作的,但我不明白这段代码中的一件事。在void*函数中返回int就像一个咒语,但是返回float就不是了。