passing env. variables to downstream job after job failed - jenkins

I have a jenkins upstream job, which on failure will trigger the downstream job, but I need to pass the same env. variable of upstream job in the downstream job.
I am using powershell to set the env. variables like $env:tag=$(git describe) i.e generating my git tag. How can I send this env. variable in the downstream job, without using the git url in the downstream job.
And the downstream job should only get triggered on failure of upstream job.
I have used triggered parameterized build plugin by storing the env. variable in a txt file (echo "$env:tag=$(git describe)" > env.txt) but this also not working.
I have tried few other plugins but nothing working out.
usecase: JobA wants to pass its env. variable set in the powershell ($ENV:tag) to JobB. Therefore in the configuration of JobA the predefined parameters textfield is used to resolve the name but does not work as expected. Instead the whole string "$ENV:tag" is passed instead of "env-value". Here how I configured it:
– JobA-------
predefined parameters: gittag=$ENV:tag =>pass parameter on to JobB
– JobB--------
echo gittag =>output: echo $ENV:tag => $ENV:tag

You can use Parameterized Trigger Plugin.
Here is the link for more details: https://wiki.jenkins.io/display/JENKINS/Parameterized+Trigger+Plugin

This appears to be a known issue with this plugin.
If the downstream job is only triggered when the upstream job fails, then do not make the downstream job a parameterized job. Instead, write the variables needed from the upstream job to a property file in the downstream job's workspace.
echo Var1=value>../Downstream_Job_Folder/downstream.properties
echo Var2=value>>../Downstream_Job_Folder/downstream.properties
In the downstream job, use the EnvInject Plugin as your first build step, or write a script to read the vars from the file.

PASSING ENV. VARIABLES FROM UPSTREAM TO DOWNSTREAM JOB IN JENKINS
. write the variables needed from the upstream job to a property( IN OUR CASE
env.properties file) file in the downstream job's workspace.
echo Var1=value>../Downstream_Job_Folder/downstream.properties
echo Var2=value>>../Downstream_Job_Folder/downstream.properties
---------- IN MY CASE -------------
$PSDefaultParameterValues['Out-File:Encoding'] = 'utf8'
$commit_id=$(git rev-parse --short HEAD)
$tag=$(git describe)
echo var1=$commit_id > "C:\Program Files
(x86)\Jenkins\workspace\powershell_2\env.properties"
echo var2=$tag >> "C:\Program Files
(x86)\Jenkins\workspace\powershell_2\env.properties"
echo $commit_id
echo $tag # TO CROSS-CHECK
. In the downstream job, use the EnvInject Plugin as your first build step, AND
- give Properties File Path - env.properties
. Then choose the second build step as windows powershell , and for windows powershell to
read the env.properties file , use below commands
- $AppProps = convertfrom-stringdata (get-content env.properties -raw)
$AppProps.'var1' # will print the var1 value
$AppProps.'var2' # will print the var2 value
$env:commit_id=$AppProps.'var1'
$env:tag=$AppProps.'var2'
echo git:$env:tag
echo git:$env:commit_id # this will print the desired output
----------In case of linux -------------------
. IN THE UPSTREAM JOB
- echo "name=##" > /home/jenkins/jenkins/workspace/sh_tst_2/env.properties
- echo "age=22" >> /home/jenkins/jenkins/workspace/sh_tst_2/env.properties
. In the downstream job, use the EnvInject Plugin as your first build step, AND
- give Properties File Path - env.properties
. Then choose the second build step as LINUX SHELL
echo $name
echo $age # WILL GIVE U THE OUTPUT OF THE ENV. VAR FROM UPSTREAM JOB

Related

Passing workspace url of Job A to Job B in Jenkins

I have two pipeline jobs Job A and Job B. I need to pass the workspace url of Job A (say /var/lib/jenkins/workspace/JobA) to be used by Job B. The main idea is I am trying to copy the contents of target folder which is generated due to maven build but I don't want to use Copy Artifacts Plugin or Archive Artifacts Plugin to achieve the same.
I have tried using the option "This job is parameterized" where Job A is the upstream of Job B but i am unable to so using that option.
Can anyone help to achieve the same ?
The WORKSPACE variable is an env variable from Jenkins and is pointing like / .
For eg.
If the job name is Job_A --> the workspace value will be <jenkins_path>/Job_A
For eg.
If the job name is Job_B --> the workspace value will be <jenkins_path>/Job_B
So you can't use the WORKSPACE var and expects the Job_B to point to Job_A workspace value.
The below can be used to get certain properties from the upstream job.
Jenkins - How to get and use upstream info in downstream
Even if you want to hard code it in the Job_B it will be fine(not recommended)
Also for this to work your node should be same for both the jobs
I have found a way to do the same and it is working fine.
I have made the Job B a parameterized job using "This project is parameterized" and used string parameter.
Then, in the pipeline script of Job A, i invoked the Job B by passing WORKSPACE env variable. Here is the declarative pipeline script for Job A:
pipeline {
agent any
stages
{
stage ('Build JobB')
{
steps {
build job: 'jobB', parameters: [string(name: 'UPSTREAM_WORKSPACE', value: "${env.WORKSPACE}")]
}
}
} }
Now, in Job B pipeline you can try to echo the variable UPSTREAM_WORKSPACE. This is how we can pass the workspace url and use it to copy the artifacts.

Jenkins - How to get and use upstream info in downstream

Executing upstream job called "A". On success of A executing test cases which is downstream project "B". But while sending mail from B we have to incorporate upstream project details (upstream project name, build no) in mail. So we can easily map / corelate the test run with respective upstream job.
In downstream project dashboard below details are displaying.
Started by upstream project Dev_RM_3.0_CI_Test build number 10
originally caused by:
I checked in https://wiki.jenkins-ci.org/display/JENKINS/Building+a+software+project. but couldnt find anything to inherit in downstream.
Created sample job with below details to display the current job details.
echo $BUILD_NUMBER
echo $JOB_NAME
echo $BUILD_ID
But the output is
Building on master in workspace /var/lib/jenkins/workspace/env
[env] $ /bin/sh -xe /tmp/hudson970280339057643719.sh
+ echo 1
1
+ echo env
env
+ echo 1
1
Finished: SUCCESS
Any help to inherit upstream details in downstream job?
How to get current job details?
The message that you refer to your question "Started by upstream project "Chained/1-First" build number 34" for example, is available in the jenkins Cause.
Jenkins keeps the upstream build info in it's cause object. If your are using build DSL or Pipelines you may get it in groovy. Alternatively you can curl the job url and use jq to get the Cause
For example curl http://localhost:8080/job/Chained/job/2-Second/17/api/json
"_class": "org.jenkinsci.plugins.workflow.job.WorkflowRun",
"actions": [{
"_class": "hudson.model.CauseAction",
"causes": [{
"_class": "hudson.model.Cause$UpstreamCause",
"shortDescription": "Started by upstream project \"Chained/1-First\" build number 34",
"upstreamBuild": 34,
"upstreamProject": "Chained/1-First",
"upstreamUrl": "job/Chained/job/1-First/"
}]
}
Or from the pipeline for example:
node() {
stage('downstream') {
def upstream = currentBuild.rawBuild.getCause(hudson.model.Cause$UpstreamCause)
echo upstream?.shortDescription
}
}
You can get a bunch of information out of Cause, pending all the script approvals or a global shared step. You will get a null if a different cause triggers this build, eg commit, or user.
You can pass in the upstream variables via build parameters to the downstream job and then you can access them (in the downstream job) using things such as ${MyParameter1} and ${MyParameter2}.
You would need to:
Add build parameters to the downstream job. For example, a string parameter named "ParentJobName".
Add a post build "Trigger downstream parameterized builds on other projects" to the upstream job.
Add something like "Current Build parameters" or "Predefined parameters" to the #2 and pass in whatever you need. For example:
ParentJobName=${JOB_NAME}
Access the parameters as you would other build variables. e.g. ${ParentJobName}
You should be able to pass in the basic stuff that way. Anything more complicated than that and you will probably be better off using a plugin like Copy Artifacts Plugin to copy files or using the Jenkins API in a system groovy step to get/modify the upstream build, etc.
You can simply use params.variableName in your downstream job to retrieve the parameters passed from your upstream parameter job. Your downstream job need not necessarily be a parameterized job.
Extending #razboy answer:
this is good way if Cause cannot be whitelisted in sandbox. I forgot about Jenkins API and used current build console to look for string about trigger cause. You can try to fetch data from API as #razboy or get current console and grep it if you need simple stuff. Jenkins API is more flexible for more complex logic. To get API help,append /api to your build url: <jenkins_url>/job/<buildUrl>/<buildNumber>/api
def buildUrl = env.BUILD_URL
sh "wget $buildUrl -O currentConsole.txt"
statusCode = sh returnStatus: true,script: 'cat currentConsole.txt | grep -q "Started by upstream project"'
boolean startedByUpstream= statusCode==0
MeowRude's answer helped me. To repcap it, in upstream job:
build job: 'mail-test', parameters: [[$class: 'StringParameterValue', name: 'VERSION_NUMBER', value: '1.0.0.0']]
And in downstream job:
echo "${params.VERSION_NUMBER}"
You may have to have certain plugins installed, but
def causes = currentBuild.getBuildCauses()
will return an ArrayList of objects that will most likely provide the necessary details, for example upstreamProject for the full project name and upstreamBuild for the build number. Then you can correlate results between up- and downstream builds easily.
Source: link to pipeline-examples in razboy's comment above

Passing variable from shell script to jenkins

I trigger a shell script from Jenkins, This scripts get date and export it as a environment(Linux) variable $DATE. I need to use this $DATE inside same Jenkins job. I made job as parameter build. Created a string parameter as DATE value as DATE=$DATE. But it is not working.
Please suggest !!
You mention that you are exporting a DATE environment variable in an shell script, which is presumably being started via an "Execute shell" step.
The problem is, once the shell step has completed, that environment is gone — the variables will not be carried over to subsequent build steps.
So when you later try to use the $DATE value — whether in another build step, or as a parameter to another job — that particular environment variable will no longer exist.
What you can do instead is use the EnvInject plugin to export environment variables during a build. Variables set up using this plugin will be available to all subsequent build steps.
For example, you could write the DATE to a properties field in one build step:
echo DATE=$(date +%Y-%m-%d) > env.properties
Then you can add an "Inject environment variables for your job" build step, and enter env.properties in the "Environment Properties File Path" field.
That way, the DATE variable (and anything else in that properties file) will be exported and will be visible to the rest of the build steps.
You could use an assignment statement and sh's returnStdout to get the value in Jenkins without having to write to a properties file.
foo = sh(
returnStdout: true,
script: 'date'
)
Then later on in the Jenkinsfile you can use $foo like any other variable.
EDIT: This is for a pipeline job, not a freestyle job.
I had the same issue.
The solution that worked for me was:
env.ABC=bat(returnStdout: true,
script: ''' #echo off echo abc ''').trim()
The .trim() and #echo off is important if you want to reuse the variable in another batch script.

Is there any way to configure Jenkins without using GUI?

I want to setup master and slave relationship in Jenkins without opening the jenkins link.
Is it possible to change the config.xml and form this setup?
The value of slave node will be passed as parameter and will be put in the config file.
If I understand your question correctly, you can try this following solution. Actually my current Test framework is working as CI configured just like you want. What you need to do is:
find suitable Plugin that you can use and support
set your Jenkins jobs to get configurations form your Code project e.g. from VCS
(goto Job Config > Source Code Management > Check-out Strategy must be set to 'as much as possible')
This can be done in following steps:
install Powershell/Batch plugin for Jenkins
prepare update script and put it in your code project
every time you need to configure your Jenkins job, just set properties in your script
update/commit your code project into the VCS
run your Jenkins job
As example you can use this sample batch code as configurable pre-steps:
#echo off
call %WORKSPACE%/jenkins-scripts/set-properties.bat "myRootFolder=/user/project" "rootRefDataFolder=12345" "standartVersion=1.2.3" "alwaysReload=false"
call %WORKSPACE%/jenkins-scripts/do-something-else.bat
And this one as set-properties.bat:
#echo off
echo ----------------------------------------------------------
SET PROP_NAME=base.Project.properties
echo Task: [Update %PROP_NAME%] started
echo Workspace: %WORKSPACE%
SET PROJECT_PATH=projectPath=%WORKSPACE:\=/%
SET RESULT_FOLDER=testResultFolder=report
SET PROP_PATH=%WORKSPACE%\test\resources
DEL "%PROP_PATH%\%PROP_NAME%"
echo %PROJECT_PATH%>> "%PROP_PATH%\%PROP_NAME%"
echo %RESULT_FOLDER%>> "%PROP_PATH%\%PROP_NAME%"
for %%x in (%*) do echo %%~x>> "%PROP_PATH%\%PROP_NAME%"
echo Current properties:
echo __________________________________________________________
type "%PROP_PATH%\%PROP_NAME%"
echo __________________________________________________________
echo Task: [Update %PROP_NAME%] finished
echo ----------------------------------------------------------
Just be sure to set your own paths and variables.

Updating jenkins job variable

Parameterized variable are not getting updated in jenkins
I m using the conditional build-step plugin to update the jenkins job parameter by executing shell script its showing me the new value of variable as well but its not get reflected.
You can try the EnvInject Plugin. One of the features is a build step that allows you to "inject" parameters into the build job from a settings file.
Create a property for the email list in the env.properties file:
echo "variable=`value`"> env.properties
It will create the properties file in the job workspace directory.
env.properties
In shell script:
"$variable"
If I understand correctly, you are trying to change the value of a pre-defined parameter
from within a script that is run by the job.
This will not work, because of "scope" (or "call-stack"),
as a process (your script) cannot change the environment of a parent process (your Jenkins job).

Resources