jenkins : update parameters via groovy script - jenkins

I have a text file on server, e.g. /var/lib/jenkins/.../myChoices.txt
FirstChoice,SecondChoice
As the files will updated from time to time, I want the script update the parameters every time will I click "build with parameters"
But my code only works when I build the job, i.e. is not updating in real time.
def getMyChoices() {
List<String> choices = Arrays.asList(readFileFromWorkspace('/var/lib/jenkins/.../myChoices.txt').split(','))
return choices
}
job(jobName) {
description("Deploy something based on choice.")
parameters {
...
...
choiceParam('EB_ACTIVE_ENV_NAME', getMyChoices(), '')
}
}
I do not want to use the hudson plugin too due to some vulnerability reason.

Groovy scripts would be executed only when the job is run. Hence, until the job is run, the parameters would not be refreshed
The only solution available is to this job at regular intervals with an additional flag to refresh the parameters alone and then exit.
This way whenever you click on Build on Parameters options, you will have the latest parameters that exists in the file.

It is required to regenerate the job in order to refresh the parameters.
What I would do is create a job that generates the jobs with jobdsl step when I get a change on the repository where myChoices.txt is versioned
here is an exemple of use of jobDsl
jobDsl removedJobAction: 'DELETE',
removedViewAction: 'DELETE',
targets: targetFile,
unstableOnDeprecation: true,
additionalParameters: [
pipelineJobs: arrFiles,
props: [
basePath: destination,
gitRemoteUrl: config.gitRemoteUrl,
gitConfigJenkinsBranch: config.gitConfigJenkinsBranch,
localPath: config.localPath ?: ''
]
]
I use it with a shared library I created that allows me to abstract jobDSL and only write pipelineDSL https://github.com/SAP/jenkins-pipelayer/ but there are restriction to this lib, because I parse the pipelineDSL, getMyChoices() would not be evaluated in the current version of the lib

Related

How to access stringParam in groovy Jenkins pipeline

I have a job which takes stringParam and i am trying to access that stringParam from workflow, however i am getting No such property exception.
parameters {
stringParam("COMMIT_SHA", "", "[Required] Short SHA of the commit used to build the image")
}
print "The commit sha val is: $env.COMMIT_SHA"
I have tried different options like ${params.COMMIT_SHA}, ${COMMIT_SHA}
Solution
Modify your parameters block as follows
parameters {
string(name: 'COMMIT_SHA', defaultValue: '', description: '[Required] Short SHA of the commit used to build the image')
}
You should then be able to reference it using ${params.COMMIT_SHA} or ${COMMIT_SHA} or ${env.COMMIT_SHA}
Your syntax is for the Jobs DSL plugin but you stated you are using a pipeline. If you are, in fact, using a Freestyle Job to create other jobs instead of a Pipeline please provide the entire script and I will update my answer. However, your post appears to want to set the parameter for a pipeline ( not specify the metadata for the creation of a separate job via the Jobs DSL plugin )
The following Job DSL script, when executed, will create a Job called "example" with COMMIT_SHA as a parameter. It won't be added as a parameter to the job that contains the Job DSL script
job('example') {
parameters {
stringParam('myParameterName', 'my default stringParam value', 'my description')
}
}
In other words, there is nothing to print in the job that contains the stringParam code because that code configures a different job to contain a string parameter, it doesn't add that parameter to the current job

How to access trigger event properties in a Jenkins pipeline script

I have a Jenkins job config that uses the "Build whenever the specified event is seen" trigger (supported by the Cloudbee's Notification API plugin) and specifies a Jmespath Query (e.g. ref=='refs/heads/master') and runs a pipeline script. I want to access other properties in the trigger event (e.g. repository.full_name) from within the pipeline script. How can I do this?
Found the answer. The data I was looking for is in the com.cloudbees.jenkins.plugins.pipeline.events.EventTriggerCause instance of the build causes. For example, the following code finds all the commits:
def newCommits = currentBuild.rawBuild.getCauses().findAll {
it instanceof com.cloudbees.jenkins.plugins.pipeline.events.EventTriggerCause
}.collect{
it.getEvent().commits
}

Pass large amount of parameters between jobs

I have two Jenkins jobs that tun on separate computers. On computer 1 I read properties file and use it for environment variables. But i need the same file on PC 2 and it only exist on the first one. When the first Jenkins job finishes it starts the second one and it can pass parameters file via job but I have to receive with creation of separate parameter with Parameterized Trigger Plugin for each parameter, and I have a lot and don`t want to do so. Is there simple solution for this issue?
Forget Jenkins 1 and the plugins Parameterized Trigger Plugin. Using Jenkins 2, here's an example of your need:
node ("pc1") {
stage "step1"
stash name: "app", includes: "properties_dir/*"
}
node ("pc2") {
stage "step2"
dir("dir_to_unstash") {
unstash "app"
}
}

jenkins job description: button with javascript action not created by groovy

i used the code from the answer of ...
How to submit Jenkins job via REST API?
... to insert a button to the job build descriptions.
Jenkins version : 1.645
The button is visible, but the onClick action is simply not created.
Do i have to install additional jenkins plugins to allow javascript or ajax actions? Thanks for your support!
job.builds
.findAll { build -> build.number == buildNumber }
.each { build ->
build.setDescription("""
<button
type='button'
onclick='javascript:
console.log("OnClick Action triggered!");
var another_job = function() {
new Ajax.Request("http://jenkins.alalala/hudson/job/AA_dummy_job_AUTO/build", {
method: "post",
parameters: {json: Object.toJSON({parameter: [{name: "SOME_JOB_PARA", value: "MY_VALUE"}]})}
});
};
another_job();
location.reload();'>Do Something!</button>""")
}
Generally it seems like a bad idea to inject buttons into the UI, rather than using built-in features like downstream jobs, or the Promoted Builds Plugin, or the Parameterized Trigger plugin.
But you haven't given many details — do you see your log text being output in the JS console? Are there any other errors?
For what it's worth, it should work; Ajax.Request should be available on the job page by default, and pasting that JavaScript into the JS console in Chrome works for me — a new build is started with the parameter.
Thanks to Christopher,
since the 'anything goes'-Formatter plugin is not available for jenkins versions >1.5 i use an alternative.
Promoted Builds Plugin
Fits my needs in most cases.

How to get build time stamp from Jenkins build variables?

How can I get build time stamp of the latest build from Jenkins?
I want to insert this value in the Email subject in post build actions.
Build Timestamp Plugin will be the Best Answer to get the TIMESTAMPS in the Build process.
Follow the below Simple steps to get the "BUILD_TIMESTAMP" variable enabled.
STEP 1:
Manage Jenkins -> Plugin Manager -> Installed...
Search for "Build Timestamp Plugin".
Install with or without Restart.
STEP 2:
Manage Jenkins -> Configure System.
Search for 'Build Timestamp' section, then Enable the CHECKBOX.
Select the TIMEZONE, TIME format you want to setup with..Save the Page.
USAGE:
When Configuring the Build with ANT or MAVEN,
Please declare a Global variable as,
E.G. btime=${BUILD_TIMESTAMP}
(use this in your Properties box in ANT or MAVEN Build Section)
use 'btime' in your Code to any String Variables etc..
NOTE: This changed in Jenkins 1.597, Please see here for more info regarding the migration
You should be able to view all the global environment variables that are available during the build by navigating to https://<your-jenkins>/env-vars.html.
Replace https://<your-jenkins>/ with the URL you use to get to Jenkins webpage (for example, it could be http://localhost:8080/env-vars.html).
One of the environment variables is :
BUILD_ID
The current build id, such as "2005-08-22_23-59-59" (YYYY-MM-DD_hh-mm-ss)
If you use jenkins editable email notification, you should be able to use ${ENV, var="BUILD_ID"} in the subject line of your email.
One way this can be done is using shell script in global environment section, here, I am using UNIX timestamp but you can use any shell script syntax compatible time format:
pipeline {
agent any
environment {
def BUILDVERSION = sh(script: "echo `date +%s`", returnStdout: true).trim()
}
stages {
stage("Awesome Stage") {
steps {
echo "Current build version :: $BUILDVERSION"
}
}
}
}
Try use Build Timestamp Plugin and use BUILD_TIMESTAMP variable.
Generate environment variables from script (Unix script) :
echo "BUILD_DATE=$(date +%F-%T)"
I know its late replying to this question, but I have recently found a better solution to this problem without installing any plugin. We can create a formatted version number and can then use the variable created to display the build date/time.
Steps to create: Build Environment --> Create a formatted version number:
Environment Variable Name: BUILD_DATE
Version Number Format String: ${BUILD_DATE_FORMATTED}
thats it. Just use the variable created above in the email subject line as ${ENV, var="BUILD_DATE"} and you will get the date/time of the current build.
You can use the Jenkins object to fetch the start time directly
Jenkins.getInstance().getItemByFullName(<your_job_name>).getBuildByNumber(<your_build_number>).getTime()
also answered it here:
https://stackoverflow.com/a/63074829/1968948
BUILD_ID used to provide this information but they changed it to provide the Build Number since Jenkins 1.597. Refer this for more information.
You can achieve this using the Build Time Stamp plugin as pointed out in the other answers.
However, if you are not allowed or not willing to use a plugin, follow the below method:
def BUILD_TIMESTAMP = null
withCredentials([usernamePassword(credentialsId: 'JenkinsCredentials', passwordVariable: 'JENKINS_PASSWORD', usernameVariable: 'JENKINS_USERNAME')]) {
sh(script: "curl https://${JENKINS_USERNAME}:${JENKINS_PASSWORD}#<JENKINS_URL>/job/<JOB_NAME>/lastBuild/buildTimestamp", returnStdout: true).trim();
}
println BUILD_TIMESTAMP
This might seem a bit of overkill but manages to get the job done.
The credentials for accessing your Jenkins should be added and the id needs to be passed in the withCredentials statement, in place of 'JenkinsCredentials'. Feel free to omit that step if your Jenkins doesn't use authentication.
This answer below shows another method using "regexp feature of the Description Setter Plugin" which solved my problem as I could not install new plugins on Jenkins due to permission issues:
Use build timestamp in setting build description Jenkins
If you want add a timestamp to every request from browser to jenkins server.
You can refer to the jenkins crumb issuer mechanism, and you can hack the /scripts/hudson-behavior.js add modify here. so it will transform a timestamp to server.
/**
* Puts a hidden input field to the form so that the form submission will have the crumb value
*/
appendToForm : function(form) {
// add here. ..... you code
if(this.fieldName==null) return; // noop
var div = document.createElement("div");
div.innerHTML = "<input type=hidden name='"+this.fieldName+"' value='"+this.value+"'>";
form.appendChild(div);
}

Resources