Jenkins build failed due to command not being recognized - jenkins

I have this build error saying pandoc command is not recognize, when I build my pipeline on Jenkins :
But when I run the exact same command using cmd.exe from the same repository it works perfectly :
So what's wrong here, my command pandoc is well installed and can perfectly be used from cmd.exe, why doesn't it works from Jenkins ?
Here is my Jenkins code (the part causing the error is in the "Build" stage):
pipeline {
agent any
stages {
stage('Prerequisites') {
steps {
//bat 'RMDIR C:\\wamp64\\www\\html\\doc'
bat 'MKDIR C:\\wamp64\\www\\html\\doc'
}
}
stage('Build') {
steps {
bat 'pandoc -s C:\\wamp64\\www\\index.md -o C:\\wamp64\\www\\index.html'
bat 'pandoc -s C:\\wamp64\\www\\index.md -o C:\\wamp64\\www\\index.docx'
}
}
stage('Deploy') {
steps {
bat 'COPY C:\\wamp64\\www\\index.html COPY C:\\wamp64\\www\\html\\index.html'
bat 'COPY C:\\wamp64\\www\\index.docx COPY C:\\wamp64\\www\\html\\doc\\index.docx'
}
}
}
}
Thanks for helping.

Jenkins doesn't automatically take your Windows (path) environment variables. Instead, what you need to do is to go to Jenkins -> Configure System -> Global properties -> Environment variables and add a new variable called Path. For the value, set $Path, and your path variables should start getting registered.
The issue has been discussed extensively in this question.

Related

variable does not get resolved in my jenkinsfile

I am new to jenkins/groovy and I am currently facing following issue...
I defined a deployment pipeline in a jenkinsfile, it consists in deploying scripts on two different environments running under linux. Deployment script copy_files.sh has to run under a specific user to preserve permissions:
def my_dst = '/opt/scripts'
pipeline {
agent { label '<a generic label>' }
stages {
stage('Deployment env1') {
agent { label '<a specific label>' }
steps {
script {
echo 'Deploying scripts...'
sh '/bin/sudo su -c "${WORKSPACE}/copy_files.sh ${WORKSPACE} ${my_dst}" - <another user>'
}
}
}
stage('Deployment env2') {
agent { label '<another specific label>' }
steps {
script {
echo 'Deploying scripts...'
sh '/bin/sudo su -c "${WORKSPACE}/copy_files.sh ${WORKSPACE} ${my_dst}" - <another user>'
}
}
}
}
}
I defined the destination path where files are supposed to be copied as a variable (my_dst same on both envs). While the env variable $WORKSPACE gets resolved my variable my_dst does not, resulting in an abort of the copy_files.sh script because of missing argument...
How can I quote my command properly in order my variable to be resolved? running sudo command with hard-coded destination path /opt/scripts works.
txs in advance
So you want Groovy to inject the my_dst, but the WORKSPACE to come from the shell environment, so you will need to use double quotes (so groovy does the templating), and escape the $ in WORKSPACE so Groovy doesn't template it and it gets passed to the shell as-is:
sh "/bin/sudo su -c \"\${WORKSPACE}/copy_files.sh \${WORKSPACE} ${my_dst}\" - <another user>"

unable to override env PATH variable in Jenkins

In Jenkins Server, there are two global environment variables defined. It's in Manage Jenkins -> Configure System -> Global Properties -> Environment variables
Name: MAVEN_HOME
Value: /var/home/tools/hudson.tasks.Maven_MavenInstallation/maven3.5.2
Name: PATH+EXTRA
$PATH:/usr/local/bin:$MAVEN_HOME/bin
I see that PATH+EXTRA will add the MAVEN PATH to the PATH environment variable. This is how my existing Server set up is. Now I need to update Jenkins with Maven 3.8.2, so I downloaded Maven 3.8.2 in the server using Manage Jenkins -> Global Tool Configuration -> Maven Installations. Now I am trying to override the global MAVEN_HOME and PATH to point to MAVEN_3.8.2 path.
In the Jenkins pipeline script
def maven_version = 'maven_3.8.2'
pipeline {
agent any
stages {
stage ('build') {
steps {
withEnv(["PATH+MAVEN=${tool maven_version}/bin"]) {
echo "PATH is: $PATH"
echo env.PATH
echo env.MAVEN_HOME
sh 'env'
sh 'mvn --version'
}
}
}
}
}
Results:
echo "PATH is: $PATH" =>
/var/home/tools/hudson.tasks.Maven_MavenInstallation/maven_3.8.2/bin:/opt/java/jdk/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/local/bin:/var/home/tools/hudson.tasks.Maven_MavenInstallation/maven_3.5.2/bin:/opt/java/jdk/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
echo env.PATH => /var/home/tools/hudson.tasks.Maven_MavenInstallation/maven_3.8.2/bin:/opt/java/jdk/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/local/bin:/var/home/tools/hudson.tasks.Maven_MavenInstallation/maven_3.5.2/bin:/opt/java/jdk/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
echo env.MAVEN_HOME =>
/var/home/tools/hudson.tasks.Maven_MavenInstallation/maven_3.5.2
sh 'env' => prints all the environment variables. Noticed following:
MAVEN_HOME=/var/home/tools/hudson.tasks.Maven_MavenInstallation/maven_3.5.2
PATH=$PATH:/usr/local/bin:/var/jenkins_home/tools/hudson.tasks.Maven_MavenInstallation/maven_3.5.2/bin:/var/jenkins_home/tools/hudson.tasks.Maven_MavenInstallation/maven_3.8.2/bin:/opt/java/openjdk/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/local/bin:/var/jenkins_home/tools/hudson.tasks.Maven_MavenInstallation/maven_3.5.2/bin:/opt/java/openjdk/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
Why is the PATH is being appending with Maven 3.5.2 in the front of the path. How can I let PATH point to Maven 3.8.2?
sh 'mvn --version' => Apache Maven 3.5.2
Maven home: /var/home/tools/hudson.tasks.Maven_MavenInstallation/maven_3.5.2
How do I get the mvn --version result with maven3.8.2?
Note: I also tried with free style project, and used following commands to override the values but the mvn --version is always printing 3.5.2. Any idea if it is a bug with Jenkins unable to override the path or is there any way to do it?
export MAVEN_HOME=/var/home/tools/hudson.tasks.Maven_MavenInstallation/maven_3.8.2
export PATH=$PATH:$MAVEN_HOME/bin
The format you used to modify the PATH variable uses concatenation that prepends the new value to the existing one. It means that
PATH+MAVEN=${tool maven_version}/bin
is an equivalent of:
PATH=${tool maven_version}/bin:$PATH
You can solve this issue by overriding the PATH variable explicitly and putting the new path at the end of the variable. Try to test the pipeline like this one:
def maven_version = 'maven_3.8.2'
pipeline {
agent any
stages {
stage ('build') {
steps {
withEnv(["PATH=${tool maven_version}/bin:$PATH"]) {
echo "PATH is: $PATH"
echo env.PATH
echo env.MAVEN_HOME
sh 'env'
sh 'mvn --version'
}
}
}
}
}

'.' is not recognized as an internal or external command for Gradle command in Jenkins when gradlew script is executed

I try to run SonarQube analysis for a Gradle project in a Jenkins Pipeline using the following code:
stage('SonarQube') {
withGradle {
withSonarQubeEnv('SonarQube Env') {
bat "./gradlew sonarqube"
}
}
}
The Gradle plugin is installed in Jenkins but I am getting the following error:
05:15:05 D:\*\*\*\*\*\*>./gradlew sonarqube
05:15:05 '.' is not recognized as an internal or external command,
Two things are incorrect in your code. On Windows machines you have to:
use backslashes instead of slashes in paths (./command → .\command)
execute script written for Windows (gradlew is a Unix script, gradlew.bat is a Windows script)
This code should work:
stage('SonarQube') {
withGradle {
withSonarQubeEnv('SonarQube Env') {
bat '.\\gradlew.bat sonarqube'
}
}
}
Gradle Wtapper by default is provided with two script gardlew and gradlew.bat. If your project doesn't have the gradlew.bat file, execute on your Unix machine ./gradlew wrapper. The missing file will be generated.
Btw. You don't need the Jenkins Gradle plugin, when you use Gradlew Wrapper. The plugin is required when you want to provide Gradle installations for jobs, example:
stage('SonarQube') {
withGradle {
withSonarQubeEnv('SonarQube Env') {
bat "${tool(name: 'toolId', type: 'gradle')}\\bin\\gradle.bat sonarqube"
}
}
}
toolId must much the identifiers used in the Jenkins Global Tool Configuration, examples: gradle-6.X, gradle-6.8.3 etc.

Jenkins Pipeline: Executing a shell script

I have create a pipeline like below and please note that I have the script files namely- "backup_grafana.sh" and "gitPush.sh" in source code repository where the Jenkinsfile is present. But I am unable to execute the script because of the following error:-
/home/jenkins/workspace/grafana-backup#tmp/durable-52495dad/script.sh:
line 1: backup_grafana.sh: not found
Please note that I am running jenkins master on kubernetes in a pod. So copying scripts files as suggested by the error is not possible because the pod may be destroyed and recreated dynamically(in this case with a new pod, my scripts will no longer be available in the jenkins master)
pipeline {
agent {
node {
label 'jenkins-slave-python2.7'
}
}
stages {
stage('Take the grafana backup') {
steps {
sh 'backup_grafana.sh'
}
}
stage('Push to the grafana-backup submodule repository') {
steps {
sh 'gitPush.sh'
}
}
}
}
Can you please suggest how can I run these scripts in Jenkinsfile? I would like to also mention that I want to run these scripts on a python slave that I have already created finely.
If the command 'sh backup_grafana.sh' fails to execute when it actually should have successfully executed, here are two possible solutions.
1) Maybe you need a dot slash in front of those executable commands to tell your shell where they are. if they are not in your $PATH, you need to tell your shell that they can be found in the current directory. here's the fixed Jenkinsfile with four non-whitespace characters added:
pipeline {
agent {
node {
label 'jenkins-slave-python2.7'
}
}
stages {
stage('Take the grafana backup') {
steps {
sh './backup_grafana.sh'
}
}
stage('Push to the grafana-backup submodule repository') {
steps {
sh './gitPush.sh'
}
}
}
}
2) Check whether you have declared your file as a bash or sh script by declaring one of the following as the first line in your script:
#!/bin/bash
or
#!/bin/sh

Pipeline step having trouble resolving a file path

I am having trouble getting a shell command to complete in a stage I have defined:
stages {
stage('E2E Tests') {
steps {
node('Protractor') {
checkout scm
sh '''
npm install
sh 'protractor test/protractor.conf.js --params.underTestUrl http://192.168.132.30:8091'
'''
}
}
}
}
The shell command issues a protractor call which takes a config file argument, but this file fails to be found when protractor tries to retrieve it.
If I take a look at the workspace directory for where the repo is checked out to from the checkout scm step I can see the test directory is present with the config file present the sh step is referencing.
So I'm unsure why the file cannot be found.
I thought about trying to verify the files that can be seen around the time the protractor command is being issued.
So something like:
stages {
stage('E2E Tests') {
steps {
node('Protractor') {
checkout scm
def files = findFiles(glob: 'test/**/*.conf.js')
sh '''
npm install
sh 'protractor test/protractor.conf.js --params.underTestUrl http://192.168.132.30:8091'
'''
echo """${files[0].name} ${files[0].path} ${files[0].directory} ${files[0].length} ${files[0].lastModified}"""
}
}
}
}
But this doesnt work, I dont think findFiles can be used inside a step?
Can anyone offer any suggestions about what may be going on here?
Thanks
to do the debugging you were attempting (to see if the file is actually there) you could wrap the findFiles in a script (making sure your echo is before the step that fails) or use a basic find in an "sh" step like this:
stages {
stage('E2E Tests') {
steps {
node('Protractor') {
checkout scm
// you could use the unix find command instead of groovy's findFiles
sh 'find test -name *.conf.js'
// if you're using a non-dsl-step (like findFiles), you must wrap it in a script
script {
def files = findFiles(glob: 'test/**/*.conf.js')
echo """${files[0].name} ${files[0].path} ${files[0].directory} ${files[0].length} ${files[0].lastModified}"""
sh '''
npm install
sh 'protractor test/protractor.conf.js --params.underTestUrl http://192.168.132.30:8091'
'''
}
}
}
}
}

Resources