bash 詹金斯管道 sh 坏替代

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/37219348/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-08 22:18:33  来源:igfitidea点击:

Jenkins Pipeline sh bad substitution

bashjenkinsgroovyjenkins-pipeline

提问by Stephen Nichols

A step in my pipeline uploads a .tar to an artifactory server. I am getting a Bad substitution error when passing in env.BUILD_NUMBER, but the same commands works when the number is hard coded. The script is written in groovy through jenkins and is running in the jenkins workspace.

我的管道中的一个步骤将 .tar 上传到工件服务器。传入 env.BUILD_NUMBER 时出现错误替换错误,但当数字被硬编码时,相同的命令有效。该脚本是通过 jenkins 用 groovy 编写的,并在 jenkins 工作区中运行。

sh 'curl -v --user user:password --data-binary ${buildDir}package${env.BUILD_NUMBER}.tar -X PUT "http://artifactory.mydomain.com/artifactory/release-packages/package${env.BUILD_NUMBER}.tar"'

returns the errors:

返回错误:

[Pipeline] sh
[Package_Deploy_Pipeline] Running shell script
/var/lib/jenkins/workspace/Package_Deploy_Pipeline@tmp/durable-4c8b7958/script.sh: 2: 
/var/lib/jenkins/workspace/Package_Deploy_Pipeline@tmp/durable-4c8b7958/script.sh: Bad substitution
[Pipeline] } //node
[Pipeline] Allocate node : End
[Pipeline] End of Pipeline
ERROR: script returned exit code 2

If hard code in a build number and swap out ${env.BUILD_NUMBER}I get no errors and the code runs successfully.

如果在内部版本号中进行硬编码并换出,则${env.BUILD_NUMBER}不会出现错误并且代码运行成功。

sh 'curl -v --user user:password --data-binary ${buildDir}package113.tar -X PUT "http://artifactory.mydomain.com/artifactory/release-packages/package113.tar"'

I use ${env.BUILD_NUMBER} within other sh commands within the same script and have no issues in any other places.

我在同一个脚本中的其他 sh 命令中使用 ${env.BUILD_NUMBER} 并且在任何其他地方都没有问题。

回答by Stephen Nichols

This turned out to be a syntax issue. Wrapping the command in ''s caused ${env.BUILD_NUMBERto be passed instead of its value. I wrapped the whole command in "s and escaped the nested. Works fine now.

结果证明这是一个语法问题。将命令包装在''s 中导致${env.BUILD_NUMBER传递而不是它的值。我将整个命令包装在"s 中并逃脱了嵌套。现在工作正常。

sh "curl -v --user user:password --data-binary ${buildDir}package${env.BUILD_NUMBER}.tar -X PUT \"http://artifactory.mydomain.com/artifactory/release-packages/package${env.BUILD_NUMBER}.tar\""

回答by patric.schenke

Actually, you seem to have misunderstood the envvariable. In your shblock, you should access ${BUILD_NUMBER}directly.

实际上,您似乎误解了env变量。在您的sh区块中,您应该${BUILD_NUMBER}直接访问。

Reason/Explanation:envrepresents the environment inside the script. This environment is used/available directly to anything that is executed, e.g. shell scripts.

原因/说明:env代表脚本内部的环境。此环境可直接用于/可用于执行的任何内容,例如 shell 脚本。

Please also pay attention to not write anything to env.*, but use withEnv{}blocks instead.

还请注意不要向 写入任何内容env.*,而是使用withEnv{}块。

回答by kenorb

Usually the most common issue for:

通常最常见的问题是:

Bad substitution

坏替代

error is to use shinstead of bash.

错误是使用sh而不是bash.

Especially when using Jenkins, if you're using Execute shell, make sure your Commandstarts with shebang, e.g. #!/bin/bash -xeor #!/usr/bin/env bash.

特别是在使用 Jenkins 时,如果您使用的是Execute shell,请确保您的命令shebang开头,例如#!/bin/bash -xe#!/usr/bin/env bash

回答by Gary Gan

I can definitely tell you, it's all about sh shell and bash shell. I fixed this problem by specifying #!/bin/bash -xeas follows:

我可以肯定地告诉你,这完全是关于 sh shell 和 bash shell。我通过指定#!/bin/bash -xe如下解决了这个问题:

node {
    stage("Preparing"){
        sh'''#!/bin/bash -xe
            colls=( col1 col2 col3 )
            for eachCol in ${colls[@]}
            do
              echo $eachCol
            done
        '''
    }      
}

回答by avivamg

In order to Pass groovy parameters into bash scripts in Jenkins pipelines(causing sometimes bad substitions) You got 2 options:

为了将groovy 参数传递到 Jenkins 管道中的 bash 脚本中(有时会导致错误的替换),您有 2 个选项

The triple double quotes way [ " " " ]OR the triple single quotes way [ ' ' ' ]

三重双引号的方式[“”“]三联单引号的方法[‘’']

  1. In triple double quotesyou can render the normal parameter from groovy using ${someVariable},if it's environment variable ${env.someVariable}, if it's parameters injected into your job ${params.someVariable}
  1. 在三重双引号中,您可以使用 groovy 渲染普通参数${someVariable},如果它是环境变量${env.someVariable},如果它是注入到您的工作中的参数${params.someVariable}

example:

例子

     def YOUR_APPLICATION_PATH= "${WORKSPACE}/myApp/"

      sh """#!/bin/bash
      cd ${YOUR_APPLICATION_PATH}
      npm install
      """
  1. In triple single quotesthings getting little bit tricky, you can pass the parameter to environment parameterand using it by "\${someVaraiable}"or concating the groovy parameter using''' + someVaraiable + '''
  1. 在三重单引号中,事情变得有点棘手,您可以将参数传递给环境参数并通过使用它使用它"\${someVaraiable}"连接 groovy 参数''' + someVaraiable + '''

examples:

例子

   def YOUR_APPLICATION_PATH= "${WORKSPACE}/myApp/"

   sh '''#!/bin/bash
          cd ''' + YOUR_APPLICATION_PATH + '''
          npm install
    '''

OR

或者

   pipeline{
     agent { node { label "test" } }
     environment {
       YOUR_APPLICATION_PATH = "${WORKSPACE}/myapp/"
     }

     continue...
     continue...
     continue...

     sh '''#!/bin/bash
          cd "${YOUR_APPLICATION_PATH}"
          npm install
    '''

    //OR
    sh '''#!/bin/bash
          cd "${env.YOUR_APPLICATION_PATH}"
          npm install
    '''

回答by Aamir M Meman

I was having the issue with showing the {env.MAJOR_VERSION}in an artifactory of jar file . show I approaches by keeping of environment step in Jenkinsfile.

我在显示{env.MAJOR_VERSION}jar 文件的人工制品时遇到了问题。通过在 Jenkinsfile 中保持环境步骤来展示我的方法。

pipeline {
agent any
environment {
MAJOR_VERSION = 1
}

stages {
stage('build') {
  steps {
      sh 'ant -f build.xml -v'
 }
}
}
post {
 always{
   archiveArtifacts artifacts: 'dist/*.jar', fingerprint: true
 }
}
}

I got the issue solved and then it was not showing me bad substitution in my Jenkins build output. so environment step plays a more role in Jenkinsfile.

我解决了这个问题,然后在我的 Jenkins 构建输出中没有显示出错误的替代。所以环境步骤在 Jenkinsfile 中扮演着更多的角色。