尝试在管道代码中使用函数时,Jenkins运行时出错,原因可能是什么?

时间:2016-10-19 08:10:15

标签: jenkins groovy jenkins-pipeline

我使用Jenkins管道作为代码构建全自动构建过程。

我编写了以下代码,该代码应该以特定格式返回当前日期和时间,然后生成用于在Mixpanel(注释)中创建事件的链接。

这部分代码的层次结构如下 结构:

node () {
   stage ('blah'){
    // Mixpanel parameters
            MP_API_KEY = "xxxxxxxxxxxxx3897f6851c95b45f"
            MP_API_SECRET = "xxxxxxxxxxxxx79351b08afde0d24"
            MP_EXPIRE = "1588896000"
            MP_APP_PLATFORM = "Android"
            MP_BASE_URL = "http://mixpanel.com/api/2.0/annotations/create?"
            def get_current_time_date() {
                Date date = new Date();   // given date
                Calendar calendar = GregorianCalendar.getInstance(); // creates a new calendar instance
                calendar.setTime(date);   // assigns calendar to given date
                TIMEH = calendar.get(Calendar.HOUR_OF_DAY); // gets hour in 24h format
                TIMEM = calendar.get(Calendar.MINUTE);
                TIMES = calendar.get(Calendar.SECOND);
                newdate = date.format( 'yyyy-MM-dd' );
                def result = newdate + '%' + TIMEH + ':' + TIMEM + ':' + TIMES
                result
            }
            RELEASE_DATE =  get_current_time_date()
            MP_RELEASE_NOTES = ""
            DESCRIPTION = "${MP_APP_PLATFORM}%v${MP_VERSION_NAME}${MP_RELEASE_NOTES}"
            REQUEST_URL = "api_key=${MP_API_KEY}&date=${RELEASE_DATE}&description=${DESCRIPTION}&expire=${MP_EXPIRE}"
            REQUEST_URL_NO_AMPERSAND = REQUEST_URL.replaceAll('&','')
            REQUEST_URL_API_SECRET = "${REQUEST_URL_NO_AMPERSAND}${MP_API_SECRET}"
            SIGNATURE = "md5 -q -s ${REQUEST_URL_API_SECRET}".execute().text
            CURL_COMMAND = "${MP_BASE_URL}${REQUEST_URL}&sig=${SIGNATURE}".replaceAll(' ','%20')
            // End of Mixpanel parameters
    }
}

当我在Jenkins中运行构建时,它失败并出现以下错误:

org.codehaus.groovy.control.MultipleCompilationErrorsException: startup failed:
WorkflowScript: 23: Method definition not expected here. Please define the method at an appropriate place or perhaps try using a block/Closure instead. at line: 23 column: 5. File: WorkflowScript @ line 23, column 5.
       def get_current_time_date() {
       ^

1 error

    at org.codehaus.groovy.control.ErrorCollector.failIfErrors(ErrorCollector.java:310)
    at org.codehaus.groovy.control.CompilationUnit.applyToSourceUnits(CompilationUnit.java:946)
    at org.codehaus.groovy.control.CompilationUnit.doPhaseOperation(CompilationUnit.java:593)
    at org.codehaus.groovy.control.CompilationUnit.processPhaseOperations(CompilationUnit.java:569)
    at org.codehaus.groovy.control.CompilationUnit.compile(CompilationUnit.java:546)
    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.reparse(CpsGroovyShell.java:67)
    at org.jenkinsci.plugins.workflow.cps.CpsFlowExecution.parseScript(CpsFlowExecution.java:411)
    at org.jenkinsci.plugins.workflow.cps.CpsFlowExecution.start(CpsFlowExecution.java:374)
    at org.jenkinsci.plugins.workflow.job.WorkflowRun.run(WorkflowRun.java:220)
    at hudson.model.ResourceController.execute(ResourceController.java:98)
    at hudson.model.Executor.run(Executor.java:404)
Finished: FAILURE

我尝试将get_current_time_date函数从stage clouse中删除,但无济于事。

我在Groovy IDE中运行代码,它就像一个魅力,所以我猜测我错了这个代码,你能不能试着找到问题?

2 个答案:

答案 0 :(得分:2)

您需要在节点外定义方法,或者使用闭包,如错误消息所示。 Jenkins管道基于groovy,但它在语法和用法方面有一些限制(参见Wazelin)。

以下是关注代码中基本部分的示例。

1:定义节点外的方法
node () {
    stage ('blah') {
        echo get_current_time_date()
    }
}

def get_current_time_date() {
    return 'hoge'
}
2:使用闭包而不是方法
node () {
   stage ('blah') {
        def get_current_time_date = {
            return 'hoge'
        }

        echo get_current_time_date()
    }
}

答案 1 :(得分:1)

这并没有真正回答你的问题(正确的答案已经been given),但我觉得你获得所需字符串的方式是相当人为的。您可以使用这个简单的行替换您的函数

RELEASE_DATE = new Date().format('yyyy-MM-dd%H:m:s')

这将为您提供完全相同的结果,并完全避免您的问题。