Проблема в том, что вы просите Groovy интерпретировать выражение ${git_branch_name//\//_}
, а не оболочку. Использование двойных кавычек вокруг строки, которую вы передаете шагу sh
, является причиной этого. Поэтому, если вы вместо этого напишите следующее, эта первая ошибка исчезнет:
sh 'echo ${git_branch_name//\\//_}' // <- Note the single-quotes
Как правило, всегда используйте одинарные кавычки, если только вам не нужно использовать Groovy's строковую интерполяцию (см. Самый последний echo
внизу этого ответа).
Интересно, что когда я проводил тестирование, мне не понадобился шебанг (#!/bin/bash
) для указания bash, как предлагают некоторые комментарии; этот ${variable//x/y}
синтаксис замены работал в шаге sh как есть. Я думаю, что порожденный снаряд был bash. Я не знаю, так ли это всегда, или наша коробка Дженкинса была специально настроена таким образом.
Также обратите внимание, что вам нужно экранировать escape-последовательность ('\\/'
), потому что вы передаете шагу sh строковый литерал в коде groovy. Если вы не добавите этот дополнительный обратный слеш, строка, передаваемая оболочке для интерпретации, будет echo ${git_branch_name////_}
, чего она не поймет.
Но есть и другие проблемы. Во-первых, назначение вывода шага sh для branch_name
, как вы делаете, означает, что branch_name
всегда будет равно нулю. Чтобы получить стандартный вывод из строки шелл-кода, вам нужно передать дополнительный параметр returnStdout: true
в sh:
branch_name = sh (
script: 'echo ${git_branch_name//\\//_}',
returnStdout: true
).trim () // You basically always need to use trim, because the
// stdout will have a newline at the end
Для получения бонусных баллов мы можем заключить этот колл в замыкание . Я использую его достаточно часто, чтобы сделать это хорошей идеей.
// Get it? `sh` out, "shout!"
def shout = { cmd -> sh (script: cmd, returnStdout: true).trim () }
//...
branch_name = shout 'echo ${git_branch_name//\\//_}'
Но, наконец, главная проблема заключается в том, что bash (или какая-либо оболочка, которая на самом деле была создана) не имеет доступа к переменным groovy. Насколько он знает, echo ${git_branch_name}
выводит пустую строку, и, следовательно, echo ${git_branch_name//\//_}
.
У вас есть несколько вариантов. Вы можете пропустить создание .git/branch-name
и сразу же вывести результат с заменой строки git rev-parse
:
branch_name = shout 'name=$(git rev-parse --abbrev-ref HEAD) && echo ${name//\\//_}'
Или чтобы упростить дальнейшее использование функции замены строк в groovy, а не синтаксиса bash:
branch_name = shout ('git rev-parse --abbrev-ref HEAD').replace ('/', '_')
Лично я нахожу последнее немного более читабельным. YMMV. Итак, собрав все вместе, наконец:
#!groovy
def shout = { cmd -> sh (script: cmd, returnStdout: true).trim () }
// Note that I'm not declaring any variables up here. They're not needed.
// But you can if you want, just to clearly declare the environment for
// future maintainers.
node ('Nodename') {
stage ('checkout') {
checkout (scm).$Branch_Param
commit_id = shout 'git rev-parse --short HEAD'
branch_name = shout ('git rev-parse --abbrev-ref HEAD').replace ('/', '_')
echo commit_id
echo branch_name
echo "The most recent commit on branch ${branch_name} was ${commit_id}"
}
}