Необязательный логический параметр конвейера Дженкинса - PullRequest
0 голосов
/ 29 октября 2018

Я пытаюсь использовать пользовательскую функцию с логическим значением по умолчанию, которое можно переопределить. Проблема в том, что он не отменяет значение по умолчанию. Все итерации совпадают с «else».

pipeline {

  agent {
    label 'any'
  }

  stages {
    stage('Foo') {
      steps {
        doThing('/opt/prod','athos',true)
        doThing('/opt/demo','aramis',true)
        doThing('/opt/test','porthos')
        doThing('/opt/dev','dartagnan')
      }
    }
  }
}

def doThing(def targetDir, def stackName, def prod=false) {
  if ( env.prod == true ) {
    sh """
      execute-bin \
        -Dbin.target=${targetDir} \
        -Dbin.stackName=${stackName} \
        -Dbin.prod=true
    """
  } else {
    sh """
      execute-bin \
        -Dbin.target=${targetDir} \
        -Dbin.stackName=${stackName}
    """
  }
}

Ответы [ 3 ]

0 голосов
/ 29 октября 2018

Попробуйте сравнить со строковым значением:

  if ( prod == 'true' ) 

Это происходит потому, что переменные окружения всегда являются строками, а true без qoutes является логическим значением, поэтому оно никогда не равно:

рассмотрим это:

def doThing(def prod=false) {
  if ( prod == true ) {
    println 'TRUE'   
  } else {
    println 'FALSE'
  }
}

// this is how environment are passed into the pipeline from jenkins UI
doThing('true')
> FALSE
doThing('false')
> FALSE

// if environment variables were boolean (and they are not) it would be ok
doThing(true)
> TRUE
doThing(false)
> FALSE

// the current equality check is always false
println true=='true'
> false
println true=='false'
> false
0 голосов
/ 30 октября 2018

В качестве альтернативы ответу @ chenchuck вы также можете использовать params.prod, который фактически возвращает boolean и, следовательно, не требует сравнения строк:

def doThing(def targetDir, def stackName, def prod=false) {
  if ( params.prod == true ) {
  ...

Однако == true будет устаревшим. Затем его можно сократить до:

def doThing(def targetDir, def stackName, def prod=false) {
  if ( params.prod ) {
  ...

Это описано по ссылке Pipeline Syntax->Global Variables Reference на панели инструментов вашего проекта конвейера. Прокрутите вниз, пока не найдете описание глобальной переменной params (ссылка на нее должна быть JENKINS_URL/job/globalSharedLib/pipeline-syntax/globals#params). Следующее описание я скопировал из моего локального экземпляра Jenkins:

Титулы

Предоставляет все параметры, определенные в сборке, как карту только для чтения с значения различного типа. Пример:

if (params.BOOLEAN_PARAM_NAME) {doSomething()}

или для предоставления нетривиального значения по умолчанию:

if (params.get('BOOLEAN_PARAM_NAME', true)) {doSomething()}

Примечание для использования в нескольких ветвях (Jenkinsfile): шаг свойств позволяет Вы должны определить свойства задания, но они вступают в силу, когда шаг выполнить, тогда как определения параметров сборки обычно используются до начала сборки. Для удобства любые параметры на данный момент определенные в задании, которые имеют значения по умолчанию, также будут перечислены в эта карта. Это позволяет вам написать, например:

properties([parameters([string(name: 'BRANCH', defaultValue: 'master')])])
git url: '…', branch: params.BRANCH

и будьте уверены, что ветка master будет проверена даже в начальная сборка ветвления проекта, или если предыдущая сборка не указать параметры или использовать другое имя параметра.

0 голосов
/ 29 октября 2018

В вашем блоке if есть переменная env.prod и передача true в prod функциональной переменной def prod, которая отличается. Этот prod var определен только для doThing области действия функции и отличается от env.prod или просто prod, доступных в коде groovy. Если вы не измените env.prod, то всегда будет в doThing(). Либо измените его значение где-нибудь в коде (в зависимости от логики), либо попробуйте просто:

pipeline {

  agent {
    label 'any'
  }

  stages {
    stage('Foo') {
      steps {
        doThing('/opt/prod','athos',true)
        doThing('/opt/demo','aramis',true)
        doThing('/opt/test','porthos')
        doThing('/opt/dev','dartagnan')
      }
    }
  }
}

def doThing(def targetDir, def stackName, def prod=false) {
  if ( prod == true ) {
    sh """
      execute-bin \
        -Dbin.target=${targetDir} \
        -Dbin.stackName=${stackName} \
        -Dbin.prod=true
    """
  } else {
    sh """
      execute-bin \
        -Dbin.target=${targetDir} \
        -Dbin.stackName=${stackName}
    """
  }
}

Редактировать

Я постараюсь прояснить это. Я знаю, что вы можете ссылаться на переменные окружения просто по его имени:

Переменные среды доступны из кода Groovy как env.VARNAME или просто как VARNAME. Вы также можете написать в такие свойства (только используя env. Префикс):

env.MYTOOL_VERSION = '1,33' узел {ш '/ usr / local / mytool- $ MYTOOL_VERSION / bin / start'}

Но есть разница между глобальными переменными и переменными, доступными внутри области действия функции. Если бы вы добавили присваивание из переменной doThing() prod в глобальную переменную env.prod, это также сработало бы

def doThing(def targetDir, def stackName, def prod=false) {
  env.prod = prod
  if ( env.prod == true ) {
    sh """
      execute-bin \
        -Dbin.target=${targetDir} \
        -Dbin.stackName=${stackName} \
        -Dbin.prod=true
    """
  } else {
    sh """
      execute-bin \
        -Dbin.target=${targetDir} \
        -Dbin.stackName=${stackName}
    """
  }
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...