Jenkins : Sending success email only once a day (though the job is running #hourly) - jenkins

I have a jenkins job configured to run hourly. I want the success build mail to be sent as email only once a day. Email-Ext gives me the option to send emails for all success , failures etc. But what i wanted is the ability to send success email only once.

This is an old question and you have probably found your own workaround already, but I had a similar need and I thought I'd share my solution anyway. What I was trying to do was generate a once-daily summary email of jobs in a failed state. This is fundamentally very similar to sending a once-daily success report for a single job.
My solution uses a Groovy build step coupled with the Email-Ext plugin's pre-send script feature. I got the idea from the Nabble thread referenced in the comments above. See also Email-Ext Recipes on the Jenkins site.
Here's the initial groovy script that determines which builds are failed, configured under Execute System Groovy Script. You could do something similar to determine whether your build succeeded or failed:
// List the names of jobs you want to ignore for this check
ignore = [ ]
// Find all failed and unstable jobs
failed = hudson.model.Hudson.instance.getView("All").items.findAll{ job ->
job.getDisplayName() != "Daily Jenkins Job Nag" &&
!ignore.contains(job.getDisplayName()) &&
job.isBuildable() &&
job.lastCompletedBuild &&
(job.lastCompletedBuild.result == hudson.model.Result.FAILURE ||
job.lastCompletedBuild.result == hudson.model.Result.UNSTABLE)
}
// Log the job names so the build results are legible
failed.each { job ->
println(job.getDisplayName() +
" " + job.lastCompletedBuild.result +
" at build " + job.lastCompletedBuild.number +
" (" + job.lastCompletedBuild.timestamp.format("yyyy-MM-dd'T'HH:mm ZZZZ") + ")");
}
// Return failure if there are any failed jobs
return failed.size
Then, down in the Editable Email Notification section, I set the Email-Ext plugin to notify on failure. I set Content Type to Plain Text (text/plain), left Default Content empty, and set the following as the Pre-send Script:
failed = hudson.model.Hudson.instance.getView("All").items.findAll{ job ->
job.getDisplayName() != "Daily Jenkins Job Nag" &&
job.isBuildable() &&
job.lastCompletedBuild &&
(job.lastCompletedBuild.result == hudson.model.Result.FAILURE ||
job.lastCompletedBuild.result == hudson.model.Result.UNSTABLE)
}
def output = StringBuilder.newInstance()
output << "<html>\n"
output << " <body>\n"
output << "<p>Jenkins reports the following failed jobs:</p>"
output << " <ul>\n"
failed.each { job ->
url = hudson.model.Hudson.instance.rootUrl + job.url + "/" + job.lastCompletedBuild.number + "/"
output << " <li>"
output << "" + job.displayName + ""
output << " " + job.lastCompletedBuild.result
output << " at build " + job.lastCompletedBuild.number
output << " (" + job.lastCompletedBuild.timestamp.format("yyyy-MM-dd'T'HH:mm ZZZZ") + ")"
output << "</li>\n"
}
output << " </ul>\n"
output << " </body>\n"
output << "</html>"
msg.setContent(output.toString(), "text/html")
The key is that you have access to the msg object, which is a MimeMessage. You can set the content of the MIME message to whatever you want.
In this case, I'm generating a list of failed jobs, but in your case it would be whatever message you want to receive for your once-daily success report. Depending on what you need, you could have Email-Ext send a result for every build rather than just for failed builds.

How about suppressing e-mails if insufficient time has lapsed since the previous e-mail? Although not precisely what was requested, a pre-send script like this might be worth considering for its simplicity?
if (build.result != hudson.model.Result.SUCCESS) {
cancel = true;
}
else {
try {
long minEmailGap = 1000 * 60 * 60 * 16; // 16 hours in milliseconds
File file = new File("/TimestampForMyJob.txt");
if (file.exists() == false) {
file.createNewFile();
}
else {
long currentTime = (new Date()).getTime();
if (file.lastModified() + minEmailGap > currentTime) {
cancel = true;
}
else {
file.setLastModified(currentTime);
}
}
}
catch(IOException e) {
// We can't tell whether the e-mail should be sent out or not, so we do nothing
// and it just gets sent anyway - probably the best we can do with this exception.
}
}

Well, there is no plugin that can do that for you. The default email feature in Jenkins is very simple and it works fine. There is Email-ext plugin though, and this one can do lot more for you.
First of all, with Email-ext, you can configure a specific trigger to send the email notification - it can be on success or failure, which is similar to the default behaviour of Jenkins. But then you have the more refined one, like First failure and Still failing. This will give you a great deal of control on when and to whom (Recipients list, Commiter or Requester) your Jenkins will send an email. In my case a good configuration here will help a lot with email traffic generated by Jenkins. And you can send specific emails in specific situation to specific list of people - great!
The other option, if you really do not need that level of control and want to just to limit the email traffic to one summary per day is to set up a mailing list. Most mailing list engines will let you send a daily digest of all email traffic to the list. It should be enough, although I really do not feel like it is actually a good option on the long term. I would definitely give a try to Email-ext plugin.

Related

How to make daily Jenkins Jobs Summary Report send to mail in Table format

I tried my best to search and make sure this is not duplicate questions. but didn't get any. so writing it now.
We have Daily Scheduled jobs which runs in night time for our application. so we have our support team who actually make sure all jobs went successfully every night. if not raise a ticket/concern.
Now, Support team checks all this Jobs by going to Jenkins.
We are now looking for option to make this monitoring automated by sending in mail to all stakeholders.
Being said that I have 10 jobs which I want all those jobs listed in a table with Status of execution of last night and send to group of people.
How can we achieve this? is there any Jenkins Plugin which can help us?
Thanks in Advance.
Unfortunately, I was not allowed to use API in our Jenkins due to some security constraints.
so had to go with below solution.
(have added only stage which we need for getting job status. feel free to edit/update as you need)
stage('Get status of Jobs') {
steps {
script {
env.mailText=""
def mailText = "============================================= \n"
//Add your all jobs name in a list.
allDailyJobs = ['Prod/Daily-Jobs/dbBackups', 'Prod/Daily-Jobs/productImport']
allDailyJobs.each() { jobName ->
//Remove the path prefix to get only Job name (to mention in mail report)
def regex = ~"^Prod/Daily-Jobs/"
String just_job_name = jobName - regex
// Get the Job Latest Details
def job_number = getBuildNumber(jobName)
def job_result = getBuildStatus(jobName)
//echo is paragraph format with lines sepearators
mailText = mailText + " Daily Job Name => ${just_job_name} \n"
mailText = mailText + " Build number => ${job_number} \n"
mailText = mailText + " Build Status => ${job_result} \n"
mailText = mailText + " ============================================= \n\n"
}
env.mailText = mailText
}
}
}
// Get the Last Build Numnber for the job.
#NonCPS
def getBuildNumber(String jobName) {
def job = jenkins.model.Jenkins.instance.getItemByFullName(jobName)
return job.getLastBuild().getNumber()
}
// Get the Status of the Job
#NonCPS
def getBuildStatus(String jobName) {
def job = jenkins.model.Jenkins.instance.getItemByFullName(jobName)
return job.getLastBuild().getResult().toString()
}
This stage gives "env.mailText" value which has all jobs details you need. we can use this one to send in mail or chats or to any Hooks.
Important point : this would require script approval in Jenkins to execute the task. so please make sure you have right access for it.
(to avoid this happening again and again, use it without sandbox checkout)
this is how it looks in mail.

Send email from Jenkins about total number of builds/ deployments done

I need to send email at the end of day from Jenkins to Sr.Manager about:
(count)Number of Builds , Deployments done for each project in a day.
Eg:
Builds done for today : xx(count) along with the user details( who triggered the build).
Dev deployment done today : y(count) along with the user details( who triggered the deployments).
Stage deployment done today : z(count) along with the user details( who triggered the deployments).
you should create a groovy script to create it , here is a good examples to start with - https://gist.github.com/mubbashir/484903fda934aeea9f30
another great examples are here - https://wiki.jenkins.io/display/JENKINS/Jenkins+Script+Console
this one count all builds , you need to modify it per day and that's it
Hudson.instance.getAllItems(AbstractProject.class).each {project ->
def results = [:]
def total =0
results."$project.name" = [SUCCESS:0,UNSTABLE:0,FAILURE:0,ABORTED:0]
def build = project.getLastBuild()
while (build){
//println "$project.name;$build.id;$build.result"
results."$project.name"."$build.result" = results."$project.name"."$build.result" +1
build=build.getPreviousBuild()
total = total +1
}
if (total > 50){
println "$project.name : $total"
}
results.each{name,map->
map.each{result,count->
println "$name : $result = $count"
}
}
}
"Done"

Forcing jenkins to start the build number at x

Is there a way in Jenkins to force the build number to start at 199 for example?
Since we have used cruise control for a number of years, I would like the build number is to continue from there if possible.
Please see here: https://stackoverflow.com/a/49053851/1662268
resetNumberTarget = 14
item = Jenkins.instance.getItemByFullName("Project Name [from project Dashboard]")
//println(item)
item.builds.each() { build ->
//println(build)
//println(build.number)
if(build.number >= resetNumberTarget)
{
//println("About to Delete '" + build + "'")
build.delete()
}
}
item.updateNextBuildNumber(resetNumberTarget)

Jira: Producing a report containing the stories & blocking issues associated with a release

The Company I work for uses Jira to support the requirement capture & test phases of a project. We assign stories (i.e. requirements) to a release. As a Test Engineer, I raise bugs which I then reference in the story as "Is Blocked By".
I need to create a report which lists each of the releases and the stories associated with that release. As I raise bugs, I need the report to also be populated by the bugs (or actually any other issue raised).
I cannot see a way of doing this within Jira directly but I have found a Jira module for Python... I've got the following working but now I'm stuck;
from jira import JIRA
server = {"server" : "https://jira.pxr5.hw"}
login = ('bob', 'dave')
jira = JIRA (options = server, basic_auth = login)
myProject = jira.project ("QSC")
for eachVersion in myProject.versions:
print eachVersion.name + " - " + eachVersion.id
This produces the expected output;
Release 0 - 10518
Release 0.1 - 10602
Release 0.2 - 10603
Release 1.0 - 10519
Release 2.0 - 10520
Release 3.0 - 10521
closed - 10616
work complete - 10617
From the documentation I've found, I cannot see how to return anything further by which I mean the stories under each Version and (where they exist) the bugs I've raised.
Please can you help? Thanks for your attention.
I got there in the end... Kind of... Here's a solution I found by unpicking the "raw" property...
from jira import JIRA
import sys
userName = "Dave"
userPassword = "Bob"
server = {"server" : "https://jira.pxr5.hw"}
login = (userName, userPassword)
# Open a link to Jira
jira = JIRA (options = server, basic_auth = login)
# Return an object comprising the project we're working on
myProject = jira.project ("quark")
# Get a list of the releases in the project. Notice that the version
# has to be surrounded by single quotes as it may have spaces in it
for eachVersion in myProject.versions:
jqlStatement = "project=quark AND fixVersion='" + eachVersion.name + "'"
print eachVersion.name
# Get a list of stories accociated with each release of the project
theStories = jira.search_issues (jqlStatement)
# Go through each story in the current release
for eachStory in theStories:
# The story is indented one tab with it's ID and summary name
print "\t" + eachStory.raw["key"] + " " + eachStory.raw["fields"]["summary"]
# Now get a list of issue links and go through each one
issueLinks = eachStory.raw["fields"]["issuelinks"]
for eachLink in issueLinks:
print "\t\t" + eachLink["inwardIssue"]["key"] + " " + \
eachLink["inwardIssue"]["fields"]["summary"]

CasperJs + jenkins : when a test fails, how to retrieve all information on this test

Well , I would like to know how to get back the information of a test failed in jenkins.
Here the result of my folder (fr) (it displays 22 min. but in parallel it's 3min) :
Here the description of the test failed -jenkins- :
Here the description of the test failed -casper- :
So my problem is jenkins displays only the message of the test failed, and I would like to have also useful information as line and code (in fact there is the console output but it's not convenient-> I've changed my mine, it is, see xUnit with Jenkins: how to display colors in the Build Console Output?, but I still want the information in the 'Pile d'exécution'/execution stack).
I found a solution, just change the message ... :
casper.test.on("fail", function(failure) {
failure.message = "Message : " + failure.message + "\nLine : "+ failure.line + "\nCode : " + failure.lineContents;
});
The error resume stack (with test.begin) is also modified though. But I don't care in jenkins, so we can use a condition like if casper.cli.get('xunit') { casper.test.on('fail'){...} ;}.
And so :
Rather simple actually ... I should have better search.
For Artjom :
In fact for errors it's quite verbose so I don't think there are changes to do, see :
But you can still customize it the same way and it could be something like that :
casper.test.on("fail", function(failure) {
//if error type undefined function
if(failure.message.message){//or failure.message.stack.TypeError
failure.message.message = "Message : " + failure.message.message + "\nLine : "+ failure.message.line;//in jenkins -> title
}
//else assert error
else{failure.message = "Message : " + failure.message + "\nLine : "+ failure.line + "\nCode : " + failure.lineContents;}
//console.log(JSON.stringify(failure,4,'\t')); //see parameters you can modify in the failure object
});
There isn't an error event, but different objects-properties- (compared to the type of error) in this fail event. So you can manipulate them in the way you want. But personally I'm interested by the message, the code and the line (and by default jenkins manages them with undefined error).
Now I'm working on a way to display also the screenshot path, to have something like that :
Message : No notice on the page
Line : 83
Code : this.test.assertTextDoesntExists('Notice', 'No notice on the page');
Screenshot : http://-jenkins-/job/-myJob-//lastFailedBuild/artifact/screenshots/fail0.png/
Well, I did it: https://github.com/n1k0/casperjs/pull/920
The aim is to click on the link in jenkins and display screen directly using the browser :)

Resources