Jenkins : 파이프 라인 단계에서 변수를 정의 할 수 없습니다.


106

선언적 Jenkins 파이프 라인 스크립트를 만들려고하지만 간단한 변수 선언에 문제가 있습니다.

내 스크립트는 다음과 같습니다.

pipeline {
   agent none
   stages {
       stage("first") {
           def foo = "foo" // fails with "WorkflowScript: 5: Expected a step @ line 5, column 13."
           sh "echo ${foo}"
       }
   }
}

그러나 다음 오류가 발생합니다.

org.codehaus.groovy.control.MultipleCompilationErrorsException: startup failed:
WorkflowScript: 5: Expected a step @ line 5, column 13.
           def foo = "foo"
           ^

Jenkins 2.7.4 및 Pipeline 2.4에 있습니다.

답변:


101

Jenkins Pipelines에 대한 선언적 모델에는 stage블록 에서 허용하는 제한된 구문 하위 집합이 있습니다 . 자세한 내용은 구문 가이드를 참조하세요 . 단계를 script { ... }블록 으로 래핑하여 이러한 제한을 우회 할 수 있지만 결과적으로 script블록 내에서 구문, 매개 변수 등의 유효성 검사를 잃게됩니다 .


5
스크립트 블록 외부에서 해당 변수를 사용하려면 어떻게해야합니까?
Jan Steinke

3
스크립트 블록 외부의 변수를 사용하여이 확인 stackoverflow.com/questions/43879733/...
센씰 쿠마

56

나는 오류가 지정된 줄에서 오는 것이 아니라 처음 3 줄에서 발생한다고 생각합니다. 대신 이것을 시도하십시오.

node {
   stage("first") {
     def foo = "foo"
     sh "echo ${foo}"
   }
}

유효하지 않은 추가 줄이있는 것 같습니다 ...

편집하다

declaractive에서 파이프 라인 모델 문서 , 당신이 사용해야 할 것 같다 environment예를 들어, 귀하의 변수를 선언하는 선언 블록을 :

pipeline {
   environment {
     FOO = "foo"
   }

   agent none
   stages {
       stage("first") {
           sh "echo ${FOO}"
       }
   }
}

1
스테이지에 환경 블록을 추가 할 수도 있습니다 (예 : 변수가 이전 단계에서 수행 한 작업에 의존하는 경우).
Tereza Tomcova 2018

34

@ Pom12, @abayer에 동의합니다. 답변을 완료하려면 스크립트 블록을 추가해야합니다.

다음과 같이 시도하십시오.

pipeline {
    agent any
    environment {
        ENV_NAME = "${env.BRANCH_NAME}"
    }

    // ----------------

    stages {
        stage('Build Container') {
            steps {
                echo 'Building Container..'

                script {
                    if (ENVIRONMENT_NAME == 'development') {
                        ENV_NAME = 'Development'
                    } else if (ENVIRONMENT_NAME == 'release') {
                        ENV_NAME = 'Production'
                    }
                }
                echo 'Building Branch: ' + env.BRANCH_NAME
                echo 'Build Number: ' + env.BUILD_NUMBER
                echo 'Building Environment: ' + ENV_NAME

                echo "Running your service with environemnt ${ENV_NAME} now"
            }
        }
    }
}

4
이 예에서는 jenkins에 액세스 할 수있는 정의 된 환경 변수 "ENVIRONMENT_NAME"이 이미 있다고 가정합니다.
Alberto

1
스크립트 블록이 환경 값을 변경할 수 있습니까?
pitchblack408

예, 스크립트 블록 내에서 환경 값을 변경할 수 있습니다.
NicoPaez 2011

8

Jenkins 2.138.3에는 두 가지 유형의 파이프 라인이 있습니다.

선언적 및 스크립팅 된 파이프 라인.

"선언적 파이프 라인은 파이프 라인 DSL의 새로운 확장입니다 (기본적으로 한 단계 만있는 파이프 라인 스크립트, 인수가있는 파이프 라인 단계 (지시문이라고 함)). 이러한 지시문은 특정 구문을 따라야합니다.이 새로운 형식의 요점은 더 엄격하므로 파이프 라인을 처음 접하는 사람들에게 더 쉬워야하며 그래픽 편집 등을 허용해야합니다. 스크립팅 된 파이프 라인은 고급 요구 사항을위한 대안입니다. "

젠킨스 파이프 라인 : 에이전트 대 노드?

다음은 선언적 파이프 라인에서 환경 및 전역 변수를 사용하는 예입니다. 환경이 설정된 후 정적이라고 말할 수 있습니다.

def  browser = 'Unknown'

pipeline {
    agent any
    environment {
    //Use Pipeline Utility Steps plugin to read information from pom.xml into env variables
    IMAGE = readMavenPom().getArtifactId()
    VERSION = readMavenPom().getVersion()


    }
    stages {
        stage('Example') {
            steps {
                script {
                    browser = sh(returnStdout: true, script: 'echo Chrome')
                }
            }
        }
        stage('SNAPSHOT') {
                when {
                    expression { 
                        return !env.JOB_NAME.equals("PROD") && !env.VERSION.contains("RELEASE")
                    }
                }
                steps {
                    echo "SNAPSHOT"
                    echo "${browser}"
                }
            }
            stage('RELEASE') {
                when {
                    expression { 
                        return !env.JOB_NAME.equals("TEST") && !env.VERSION.contains("RELEASE")
                    }
                }
                steps {
                    echo "RELEASE"
                    echo "${browser}"
                }
            }
    }//end of stages 
}//end of pipeline

위 코드에서 다음 오류가 발생합니다. [Pipeline] Start of Pipeline [Pipeline] readMavenPom [Pipeline] End of Pipeline org.jenkinsci.plugins.workflow.steps.MissingContextVariableException : Required context class hudson.FilePath is missing 아마도 둘러싸는 것을 잊었을 것입니다. 이 제공하는 단계와 코드 같은 : 노드
mancocapac

아니요, 그대로 작동했습니다. 선언적 파이프 라인입니다. Agent any는 모든 노드에서 작동 할 수 있음을 의미합니다
pitchblack408

@ pitchblack408, 맞습니다. 제 파이프 라인의 맨 위에 [에이전트 없음]이 있습니다. 당신이 의미하는 것이 확실하지 않습니다 : 환경이 설정된 후 정적입니까? 그들은, 스크립트 내에서 변경할 예를 들어 스크립트 {IMAGE = "된 newval} 할 수 있습니다
mancocapac

예, IMAGE를보십시오. 파이프 라인에 의해 변경 될 수 있거나 변경되어야하는 변수가 아닙니다. 환경의 일부로 정의 된 후 정적 값으로 취급되어야한다는 것이 제 이해입니다.
pitchblack408

0

Groovy 코드를 실행 하려면 스크립트 단계 가 필요한 선언적 파이프 라인 을 사용하고 있습니다. 이것은 필요하지 않은 스크립트 된 파이프 라인에 비해 큰 차이 입니다.

공식 문서는 다음을 말한다 :

스크립트 단계는 스크립팅 된 파이프 라인 블록을 가져 와서 선언적 파이프 라인에서 실행합니다.

pipeline {
   agent none
   stages {
       stage("first") {
           script {
               def foo = "foo" 
               sh "echo ${foo}"
           }
       }
   }
}
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.