原文地址:https://blog.csdn.net/u013066244/article/details/78665075
安裝插件
(安裝插件,我喜歡先去下載hpi
文件,然后再去手動安裝)
jenkins默認的郵件通知
我先講解下,默認的。
jenkins默認就有一個郵件通知,只是太簡單的,不能個性化或者說定制化。
設置系統管理員郵件地址
郵件通知
①SMTP
服務器:如果你使用的是公司郵箱,那么就詢問你自己公司里的運維人員吧;他們一般都知道,至少我就是問公司里的運維人員;要是你打算使用QQ郵箱
,那么你需要設置下,網上有教程;網易郵箱默認開啟。
說明:SMTP
是一種協議
②用戶默認郵件后綴:根據自己情況去設置
③勾選使用SMTP認證
,用戶名:根據自己情況設置,密碼也是。
④SMTP
端口:默認25
配置好了后,可以勾選 測試,在Test e-mail recipient
輸入自己的郵箱,看下能否成功。
成功后,我們可以到job
中進行配置:
配置好了后,接下來測試,我下面是故意寫錯echo
,使其構建失敗,驗證郵件。
發送郵件的結果:
可以看出這個郵件內容純文本,連個超鏈接都沒有,內容也不夠豐富!
接下來我們使用增強版的郵件通知
系統配置
在安裝好插件后,你的系統設置
里面會有這么一個設置:
接上面圖片:
上面點擊高級
按鈕后:
①SMTP server
:和之前同理
②Default user E-mail suffix
:根據自己情況填寫
③勾選Use SMTP Authentication
,用戶名和密碼填寫自己的
④SMTP port
:默認25
⑤Default Content Type
:郵件文檔類型
⑥Default Recipients
:默認接收人列表,已逗號進行分割
其他我都使用默認或者說沒有填寫,點擊保存。
注意:
上面配置中,凡是以Default
開頭的名稱,都可以在job
的配置中當做變量使用。比如:默認的收件人地址:在單獨的job
中可以這樣使用$DEFAULT_RECIPIENTS
。
單個job的單獨配置
在增加構建后操作步驟
,添加增強版郵件通知(看紅色圈住的部分):
之后你會得到:
稍微講解下:
①Disable Extended Email Publisher
:勾選后,郵件就不發送,看自己的情況嘍,如果你想調試某些東西,又不想發郵件出去就可以勾選這個。
②Project Recipient List
:收件人地址;多個收件人郵件地址用逗號進行分割;想使用全局默認配置的話,可以使用$DEFAULT_RECIPIENTS
。
③Project Reply-To List
:允許回復人的地址;想使用系統設置中的默認值的話,可以使用$DEFAULT_REPLYTO
;
④Content Type
:郵件文檔的類型,可以設置HTML
等格式;
⑤Default Subject
:默認主題,也就是郵件標題;同理可以使用$DEFAULT_SUBJECT
⑥Default Content
:默認郵件內容;這里是關鍵;我這里使用的是模板${SCRIPT, template="groovy-html.template"}
;后面會講;當然不想使用模板的話,可以通過使用jenkins
自身提供的變量來自己定義;
⑦Attach Build Log
:發送的郵件是否包含日志;
下面幾個默認就好,最后一個Triggers
非常關鍵;
假設最后一個不改的話,郵件是接收不到的,這個是官方留下的一個大坑,一定要自己再添加一個Recipient List
。
點擊保存,點擊構建后,收到的郵件格式如下:
遇到的問題
問題一
An attempt to send an e-mail to empty list of recipients, ignored.
- 1
這個問題,我一直卡着很久,差不多1天吧!始終不知道為什么收不到郵件
直到Google
到這個地方:
https://stackoverflow.com/a/37167955/6952713
問題二
Exception raised during template rendering: No signature of method: hudson.model.FreeStyleBuild.getExactRuns() is applicable for argument types: () values: [] Possible solutions: getActions(), getActions(java.lang.Class) groovy.lang.MissingMethodException: No signature of method: hudson.model.FreeStyleBuild.getExactRuns() is applicable for argument types: () values: [] Possible solutions: getActions(), getActions(java.lang.Class) at org.codehaus.groovy.runtime.ScriptBytecodeAdapter.unwrap(ScriptBytecodeAdapter.java:58) at org.codehaus.groovy.runtime.callsite.PojoMetaClassSite.call(PojoMetaClassSite.java:49) at org.codehaus.groovy.runtime.callsite.CallSiteArray.defaultCall(CallSiteArray.java:48) at org.codehaus.groovy.runtime.callsite.AbstractCallSite.call(AbstractCallSite.java:113) at org.codehaus.groovy.runtime.callsite.AbstractCallSite.call(AbstractCallSite.java:117) at SimpleTemplateScript3.run(SimpleTemplateScript3.groovy:106) at groovy.text.SimpleTemplateEngine$SimpleTemplate$1.writeTo(SimpleTemplateEngine.java:168) at groovy.text.SimpleTemplateEngine$SimpleTemplate$1.toString(SimpleTemplateEngine.java:180) at hudson.plugins.emailext.plugins.content.ScriptContent.renderTemplate(ScriptContent.java:127) at hudson.plugins.emailext.plugins.content.ScriptContent.evaluate(ScriptContent.java:68) at hudson.plugins.emailext.plugins.content.AbstractEvalContent.evaluate(AbstractEvalContent.java:64) at org.jenkinsci.plugins.tokenmacro.DataBoundTokenMacro.evaluate(DataBoundTokenMacro.java:199) at
- 1
這個錯誤是我在使用郵件模板時,報的錯!
我的步驟如下:
我在參考官方 :https://wiki.jenkins.io/display/JENKINS/Email-ext+plugin
中的Script content這一章節內容時,下載了兩個Template Examples
jenkins-matrix-email-html.template
jenkins-generic-matrix-email-html.template
按照官方教程在jenkins home
(/home/jenkins/dataspace
)目錄中創建了email-templates
文件夾,並把那兩個模板上傳上去了,之后在job
配置中的Default Content
中寫入:
${SCRIPT, template="jenkins-matrix-email-html.template"}
- 1
然后構建時,就報錯!
這一塊也困擾我很久!直到Google
到了這么一段話(網上資料真心少);
http://jenkins-ci.361315.n4.nabble.com/Email-Template-Testing-Exception-td4807117.html
內容如下:
Looks like you are trying to test a matrix template with a non matrix job.
意思是說:
看起來像你在一個非
matrix job
中測試一個matrix
模板
之后又去查詢什么是matrix job
;
這是一篇關於matrix
的官方教程
Building a matrix project
看到里面內容卻是構建一個Multi-Configuration Projects
;這時就有點迷糊了!接着查看Matrix Project Plugin
這個插件;里面的講解有這么一句話:
Multi-configuration (matrix) project type.
基本可以肯定matrix job
就是Multi-configuration project
(構建一個多配置項目)。也就是說我要使用jenkins-matrix-email-html.template
這個模板就必須創建與之對應的job
;
經過測試后,果然可以,配置都是類似的:郵件結果如下:
那么matrix job
這個用的場景多嗎?
這是官方給出的經驗:
Experience with Hudson - Building matrix project
其講解到:
比如 你的項目想在jdk 1.4 、1.5、1.6中進行測試,你就可以通過創建這種類型的
job
;
使用自定義模板
通過上面遇到的問題,我們有時會想自己來定義模板!
使用自己的模板有兩種方法:
方法一 不使用模板
在Default Content
這一欄中,自己通過Token
來寫:
(這里的token
不要翻譯成令牌,因為不知道翻譯成啥,就保留原文token
吧)
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>${ENV, var="JOB_NAME"}-第${BUILD_NUMBER}次構建日志</title>
</head>
<body leftmargin="8" marginwidth="0" topmargin="8" marginheight="4" offset="0">
<table width="95%" cellpadding="0" cellspacing="0" style="font-size: 11pt; font-family: Tahoma, Arial, Helvetica, sans-serif">
<tr>
<td>
<h2>
<font>來自Mr.Jenkins的郵件通知</font>
</h2>
</td>
</tr>
<tr>
<td>
<br />
<b><font color="#0B610B">構建信息</font></b>
<hr size="2" width="100%" align="center" />
</td>
</tr>
<tr>
<td>
<ul>
<li>項目名稱 : ${PROJECT_NAME}</li>
<li>觸發原因 :${CAUSE}</li>
<li>構建日志 : <a href="${BUILD_URL}console">${BUILD_URL}console</a></li>
<li>單元測試報告 :<a href="${BUILD_URL}testReport/">${BUILD_URL}testReport/</a></li>
<li>工作目錄 : <a href="${PROJECT_URL}ws">${PROJECT_URL}ws</a></li>
</ul>
</td>
</tr>
<tr>
<td><b><font color="#0B610B">構建日志:</font></b>
<hr size="2" width="100%" align="center" /></td>
</tr>
<tr>
<td><textarea cols="80" rows="30" readonly="readonly" style="font-family: Courier New">${BUILD_LOG}</textarea>
</td>
</tr>
</table>
</body>
</html>
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
- 31
- 32
- 33
- 34
- 35
- 36
- 37
- 38
- 39
- 40
- 41
- 42
- 43
- 44
- 45
- 46
- 47
- 48
- 49
這段代碼是從網上找來的,我好奇的是這個寫法:
${ENV, var="JOB_NAME"}
# 這個寫法其實和${JOB_NAME}、$JOB_NAME是等價的
- 1
- 2
可以理解成:
${ENV(var:JOB_NAME)}
因為參數就一個所以可以簡寫為:
${JOB_NAME}或者$JOB_NAME
- 1
- 2
- 3
方法二 使用模板
之前使用模板出錯是因為使用了matrix
項目的模板。
如果使用groovy
模板也是可以的
這是官方給的groovy
的模板:
在文件夾email-templates
,創建一個文件,比如我:
//我的路徑: /home/jenkins/dataspace/email-templates
[root@master01 email-templates] vim testy.template
// 再把官方給的模板復制粘貼進去,代碼如下:
- 1
- 2
- 3
<STYLE> BODY, TABLE, TD, TH, P { font-family:Verdana,Helvetica,sans serif; font-size:11px; color:black; } h1 { color:black; } h2 { color:black; } h3 { color:black; } TD.bg1 { color:white; background-color:#0000C0; font-size:120% } TD.bg2 { color:white; background-color:#4040FF; font-size:110% } TD.bg3 { color:white; background-color:#8080FF; } TD.test_passed { color:blue; } TD.test_failed { color:red; } TD.console { font-family:Courier New; } </STYLE>
<BODY>
<TABLE>
<TR><TD align="right"><IMG SRC="${rooturl}static/e59dfe28/images/32x32/<%= (build.result == null || build.result.toString() == 'SUCCESS') ? "blue.gif" : build.result.toString() == 'FAILURE' ? 'red.gif' : 'yellow.gif' %>" />
</TD><TD valign="center"><B style="font-size: 200%;">BUILD ${build.result ?: 'SUCCESSFUL'}</B></TD></TR>
<TR><TD>URL</TD><TD><A href="${rooturl}${build.url}">${rooturl}${build.url}</A></TD></TR>
<TR><TD>Project:</TD><TD>${project.name}</TD></TR>
<TR><TD>Date:</TD><TD>${it.timestampString}</TD></TR>
<TR><TD>Duration:</TD><TD>${build.durationString}</TD></TR>
<TR><TD>Cause:</TD><TD><% build.causes.each() { cause -> %> ${cause.shortDescription} <% } %></TD></TR>
</TABLE>
<BR/>
<!-- CHANGE SET -->
<% def changeSets = build.changeSets if(changeSets != null) { def hadChanges = false %>
<TABLE width="100%">
<TR><TD class="bg1" colspan="2"><B>CHANGES</B></TD></TR>
<% changeSets.each() { cs_list -> cs_list.each() { cs -> hadChanges = true %>
<TR>
<TD colspan="2" class="bg2"> Revision <B><%= cs.metaClass.hasProperty('commitId') ? cs.commitId : cs.metaClass.hasProperty('revision') ? cs.revision : cs.metaClass.hasProperty('changeNumber') ? cs.changeNumber : "" %></B> by
<B><%= cs.author %>: </B>
<B>(${cs.msgAnnotated})</B>
</TD>
</TR>
<% cs.affectedFiles.each() { p -> %>
<TR>
<TD width="10%"> ${p.editType.name}</TD>
<TD>${p.path}</TD>
</TR>
<% } } } if(!hadChanges) { %>
<TR><TD colspan="2">No Changes</TD></TR>
<% } %>
</TABLE>
<BR/>
<% } %>
<!-- ARTIFACTS -->
<% def artifacts = build.artifacts if(artifacts != null && artifacts.size() > 0) { %>
<TABLE width="100%">
<TR><TD class="bg1"><B>BUILD ARTIFACTS</B></TD></TR>
<TR>
<TD>
<% artifacts.each() { f -> %>
<li>
<a href="${rooturl}${build.url}artifact/${f}">${f}</a>
</li>
<% } %>
</TD>
</TR>
</TABLE>
<BR/>
<% } %>
<!-- MAVEN ARTIFACTS -->
<% try { def mbuilds = build.moduleBuilds if(mbuilds != null) { %>
<TABLE width="100%">
<TR><TD class="bg1"><B>BUILD ARTIFACTS</B></TD></TR>
<% try { mbuilds.each() { m -> %>
<TR><TD class="bg2"><B>${m.key.displayName}</B></TD></TR>
<% m.value.each() { mvnbld -> def artifactz = mvnbld.artifacts if(artifactz != null && artifactz.size() > 0) { %>
<TR>
<TD>
<% artifactz.each() { f -> %>
<li>
<a href="${rooturl}${mvnbld.url}artifact/${f}">${f}</a>
</li>
<% } %>
</TD>
</TR>
<% } } } } catch(e) { // we don't do anything } %>
</TABLE>
<BR/>
<% } }catch(e) { // we don't do anything } %>
<!-- JUnit TEMPLATE -->
<% def junitResultList = it.JUnitTestResult try { def cucumberTestResultAction = it.getAction("org.jenkinsci.plugins.cucumber.jsontestsupport.CucumberTestResultAction") junitResultList.add(cucumberTestResultAction.getResult()) } catch(e) { //cucumberTestResultAction not exist in this build } if (junitResultList.size() > 0) { %>
<TABLE width="100%">
<TR><TD class="bg1" colspan="2"><B>${junitResultList.first().displayName}</B></TD></TR>
<% junitResultList.each{ junitResult -> %>
<% junitResult.getChildren().each { packageResult -> %>
<TR><TD class="bg2" colspan="2"> Name: ${packageResult.getName()} Failed: ${packageResult.getFailCount()} test(s), Passed: ${packageResult.getPassCount()} test(s), Skipped: ${packageResult.getSkipCount()} test(s), Total: ${packageResult.getPassCount()+packageResult.getFailCount()+packageResult.getSkipCount()} test(s)</TD></TR>
<% packageResult.getFailedTests().each{ failed_test -> %>
<TR bgcolor="white"><TD class="test_failed" colspan="2"><B><li>Failed: ${failed_test.getFullName()} </li></B></TD></TR>
<% } } } %>
</TABLE>
<BR/>
<% } %>
<!-- CONSOLE OUTPUT -->
<% if(build.result==hudson.model.Result.FAILURE) { %>
<TABLE width="100%" cellpadding="0" cellspacing="0">
<TR><TD class="bg1"><B>CONSOLE OUTPUT</B></TD></TR>
<% build.getLog(100).each() { line -> %>
<TR><TD class="console">${org.apache.commons.lang.StringEscapeUtils.escapeHtml(line)}</TD></TR>
<% } %>
</TABLE>
<BR/>
<% } %>
</BODY>
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
- 31
- 32
- 33
- 34
- 35
- 36
- 37
- 38
- 39
- 40
- 41
- 42
- 43
- 44
- 45
- 46
- 47
- 48
- 49
- 50
- 51
- 52
- 53
- 54
- 55
- 56
- 57
- 58
- 59
- 60
- 61
- 62
- 63
- 64
- 65
- 66
- 67
- 68
- 69
- 70
- 71
- 72
- 73
- 74
- 75
- 76
- 77
- 78
- 79
- 80
- 81
- 82
- 83
- 84
- 85
- 86
- 87
- 88
- 89
- 90
- 91
- 92
- 93
- 94
- 95
- 96
- 97
- 98
- 99
- 100
- 101
- 102
- 103
- 104
- 105
- 106
- 107
- 108
- 109
- 110
- 111
- 112
- 113
- 114
- 115
- 116
- 117
- 118
- 119
- 120
- 121
- 122
- 123
- 124
- 125
- 126
- 127
- 128
- 129
- 130
- 131
- 132
- 133
- 134
- 135
- 136
- 137
- 138
- 139
- 140
- 141
- 142
- 143
- 144
- 145
- 146
- 147
- 148
- 149
- 150
- 151
- 152
- 153
- 154
- 155
- 156
之后把Default Content
這一欄改為:
${SCRIPT, template="testy.template"}
- 1
就可以了!
可以使用Email Template Testing
這個功能進行測試,把模板名稱輸入進去就可以啦!
假設你輸入groovy-html.template
,即使你的email-templates
文件夾里壓根沒有這個文件,也是能成功的,這是因為該插件默認內置的就是這個模板!
安裝插件
(安裝插件,我喜歡先去下載hpi
文件,然后再去手動安裝)
jenkins默認的郵件通知
我先講解下,默認的。
jenkins默認就有一個郵件通知,只是太簡單的,不能個性化或者說定制化。
設置系統管理員郵件地址
郵件通知
①SMTP
服務器:如果你使用的是公司郵箱,那么就詢問你自己公司里的運維人員吧;他們一般都知道,至少我就是問公司里的運維人員;要是你打算使用QQ郵箱
,那么你需要設置下,網上有教程;網易郵箱默認開啟。
說明:SMTP
是一種協議
②用戶默認郵件后綴:根據自己情況去設置
③勾選使用SMTP認證
,用戶名:根據自己情況設置,密碼也是。
④SMTP
端口:默認25
配置好了后,可以勾選 測試,在Test e-mail recipient
輸入自己的郵箱,看下能否成功。
成功后,我們可以到job
中進行配置:
配置好了后,接下來測試,我下面是故意寫錯echo
,使其構建失敗,驗證郵件。
發送郵件的結果:
可以看出這個郵件內容純文本,連個超鏈接都沒有,內容也不夠豐富!
接下來我們使用增強版的郵件通知
系統配置
在安裝好插件后,你的系統設置
里面會有這么一個設置:
接上面圖片:
上面點擊高級
按鈕后:
①SMTP server
:和之前同理
②Default user E-mail suffix
:根據自己情況填寫
③勾選Use SMTP Authentication
,用戶名和密碼填寫自己的
④SMTP port
:默認25
⑤Default Content Type
:郵件文檔類型
⑥Default Recipients
:默認接收人列表,已逗號進行分割
其他我都使用默認或者說沒有填寫,點擊保存。
注意:
上面配置中,凡是以Default
開頭的名稱,都可以在job
的配置中當做變量使用。比如:默認的收件人地址:在單獨的job
中可以這樣使用$DEFAULT_RECIPIENTS
。
單個job的單獨配置
在增加構建后操作步驟
,添加增強版郵件通知(看紅色圈住的部分):
之后你會得到:
稍微講解下:
①Disable Extended Email Publisher
:勾選后,郵件就不發送,看自己的情況嘍,如果你想調試某些東西,又不想發郵件出去就可以勾選這個。
②Project Recipient List
:收件人地址;多個收件人郵件地址用逗號進行分割;想使用全局默認配置的話,可以使用$DEFAULT_RECIPIENTS
。
③Project Reply-To List
:允許回復人的地址;想使用系統設置中的默認值的話,可以使用$DEFAULT_REPLYTO
;
④Content Type
:郵件文檔的類型,可以設置HTML
等格式;
⑤Default Subject
:默認主題,也就是郵件標題;同理可以使用$DEFAULT_SUBJECT
⑥Default Content
:默認郵件內容;這里是關鍵;我這里使用的是模板${SCRIPT, template="groovy-html.template"}
;后面會講;當然不想使用模板的話,可以通過使用jenkins
自身提供的變量來自己定義;
⑦Attach Build Log
:發送的郵件是否包含日志;
下面幾個默認就好,最后一個Triggers
非常關鍵;
假設最后一個不改的話,郵件是接收不到的,這個是官方留下的一個大坑,一定要自己再添加一個Recipient List
。
點擊保存,點擊構建后,收到的郵件格式如下:
遇到的問題
問題一
An attempt to send an e-mail to empty list of recipients, ignored.
- 1
這個問題,我一直卡着很久,差不多1天吧!始終不知道為什么收不到郵件
直到Google
到這個地方:
https://stackoverflow.com/a/37167955/6952713
問題二
Exception raised during template rendering: No signature of method: hudson.model.FreeStyleBuild.getExactRuns() is applicable for argument types: () values: [] Possible solutions: getActions(), getActions(java.lang.Class) groovy.lang.MissingMethodException: No signature of method: hudson.model.FreeStyleBuild.getExactRuns() is applicable for argument types: () values: [] Possible solutions: getActions(), getActions(java.lang.Class) at org.codehaus.groovy.runtime.ScriptBytecodeAdapter.unwrap(ScriptBytecodeAdapter.java:58) at org.codehaus.groovy.runtime.callsite.PojoMetaClassSite.call(PojoMetaClassSite.java:49) at org.codehaus.groovy.runtime.callsite.CallSiteArray.defaultCall(CallSiteArray.java:48) at org.codehaus.groovy.runtime.callsite.AbstractCallSite.call(AbstractCallSite.java:113) at org.codehaus.groovy.runtime.callsite.AbstractCallSite.call(AbstractCallSite.java:117) at SimpleTemplateScript3.run(SimpleTemplateScript3.groovy:106) at groovy.text.SimpleTemplateEngine$SimpleTemplate$1.writeTo(SimpleTemplateEngine.java:168) at groovy.text.SimpleTemplateEngine$SimpleTemplate$1.toString(SimpleTemplateEngine.java:180) at hudson.plugins.emailext.plugins.content.ScriptContent.renderTemplate(ScriptContent.java:127) at hudson.plugins.emailext.plugins.content.ScriptContent.evaluate(ScriptContent.java:68) at hudson.plugins.emailext.plugins.content.AbstractEvalContent.evaluate(AbstractEvalContent.java:64) at org.jenkinsci.plugins.tokenmacro.DataBoundTokenMacro.evaluate(DataBoundTokenMacro.java:199) at
- 1
這個錯誤是我在使用郵件模板時,報的錯!
我的步驟如下:
我在參考官方 :https://wiki.jenkins.io/display/JENKINS/Email-ext+plugin
中的Script content這一章節內容時,下載了兩個Template Examples
jenkins-matrix-email-html.template
jenkins-generic-matrix-email-html.template
按照官方教程在jenkins home
(/home/jenkins/dataspace
)目錄中創建了email-templates
文件夾,並把那兩個模板上傳上去了,之后在job
配置中的Default Content
中寫入:
${SCRIPT, template="jenkins-matrix-email-html.template"}
- 1
然后構建時,就報錯!
這一塊也困擾我很久!直到Google
到了這么一段話(網上資料真心少);
http://jenkins-ci.361315.n4.nabble.com/Email-Template-Testing-Exception-td4807117.html
內容如下:
Looks like you are trying to test a matrix template with a non matrix job.
意思是說:
看起來像你在一個非
matrix job
中測試一個matrix
模板
之后又去查詢什么是matrix job
;
這是一篇關於matrix
的官方教程
Building a matrix project
看到里面內容卻是構建一個Multi-Configuration Projects
;這時就有點迷糊了!接着查看Matrix Project Plugin
這個插件;里面的講解有這么一句話:
Multi-configuration (matrix) project type.
基本可以肯定matrix job
就是Multi-configuration project
(構建一個多配置項目)。也就是說我要使用jenkins-matrix-email-html.template
這個模板就必須創建與之對應的job
;
經過測試后,果然可以,配置都是類似的:郵件結果如下:
那么matrix job
這個用的場景多嗎?
這是官方給出的經驗:
Experience with Hudson - Building matrix project
其講解到:
比如 你的項目想在jdk 1.4 、1.5、1.6中進行測試,你就可以通過創建這種類型的
job
;
使用自定義模板
通過上面遇到的問題,我們有時會想自己來定義模板!
使用自己的模板有兩種方法:
方法一 不使用模板
在Default Content
這一欄中,自己通過Token
來寫:
(這里的token
不要翻譯成令牌,因為不知道翻譯成啥,就保留原文token
吧)
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>${ENV, var="JOB_NAME"}-第${BUILD_NUMBER}次構建日志</title>
</head>
<body leftmargin="8" marginwidth="0" topmargin="8" marginheight="4" offset="0">
<table width="95%" cellpadding="0" cellspacing="0" style="font-size: 11pt; font-family: Tahoma, Arial, Helvetica, sans-serif">
<tr>
<td>
<h2>
<font>來自Mr.Jenkins的郵件通知</font>
</h2>
</td>
</tr>
<tr>
<td>
<br />
<b><font color="#0B610B">構建信息</font></b>
<hr size="2" width="100%" align="center" />
</td>
</tr>
<tr>
<td>
<ul>
<li>項目名稱 : ${PROJECT_NAME}</li>
<li>觸發原因 :${CAUSE}</li>
<li>構建日志 : <a href="${BUILD_URL}console">${BUILD_URL}console</a></li>
<li>單元測試報告 :<a href="${BUILD_URL}testReport/">${BUILD_URL}testReport/</a></li>
<li>工作目錄 : <a href="${PROJECT_URL}ws">${PROJECT_URL}ws</a></li>
</ul>
</td>
</tr>
<tr>
<td><b><font color="#0B610B">構建日志:</font></b>
<hr size="2" width="100%" align="center" /></td>
</tr>
<tr>
<td><textarea cols="80" rows="30" readonly="readonly" style="font-family: Courier New">${BUILD_LOG}</textarea>
</td>
</tr>
</table>
</body>
</html>
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
- 31
- 32
- 33
- 34
- 35
- 36
- 37
- 38
- 39
- 40
- 41
- 42
- 43
- 44
- 45
- 46
- 47
- 48
- 49
這段代碼是從網上找來的,我好奇的是這個寫法:
${ENV, var="JOB_NAME"}
# 這個寫法其實和${JOB_NAME}、$JOB_NAME是等價的
- 1
- 2
可以理解成:
${ENV(var:JOB_NAME)}
因為參數就一個所以可以簡寫為:
${JOB_NAME}或者$JOB_NAME
- 1
- 2
- 3
方法二 使用模板
之前使用模板出錯是因為使用了matrix
項目的模板。
如果使用groovy
模板也是可以的
這是官方給的groovy
的模板:
在文件夾email-templates
,創建一個文件,比如我:
//我的路徑: /home/jenkins/dataspace/email-templates
[root@master01 email-templates] vim testy.template
// 再把官方給的模板復制粘貼進去,代碼如下:
- 1
- 2
- 3
<STYLE> BODY, TABLE, TD, TH, P { font-family:Verdana,Helvetica,sans serif; font-size:11px; color:black; } h1 { color:black; } h2 { color:black; } h3 { color:black; } TD.bg1 { color:white; background-color:#0000C0; font-size:120% } TD.bg2 { color:white; background-color:#4040FF; font-size:110% } TD.bg3 { color:white; background-color:#8080FF; } TD.test_passed { color:blue; } TD.test_failed { color:red; } TD.console { font-family:Courier New; } </STYLE>
<BODY>
<TABLE>
<TR><TD align="right"><IMG SRC="${rooturl}static/e59dfe28/images/32x32/<%= (build.result == null || build.result.toString() == 'SUCCESS') ? "blue.gif" : build.result.toString() == 'FAILURE' ? 'red.gif' : 'yellow.gif' %>" />
</TD><TD valign="center"><B style="font-size: 200%;">BUILD ${build.result ?: 'SUCCESSFUL'}</B></TD></TR>
<TR><TD>URL</TD><TD><A href="${rooturl}${build.url}">${rooturl}${build.url}</A></TD></TR>
<TR><TD>Project:</TD><TD>${project.name}</TD></TR>
<TR><TD>Date:</TD><TD>${it.timestampString}</TD></TR>
<TR><TD>Duration:</TD><TD>${build.durationString}</TD></TR>
<TR><TD>Cause:</TD><TD><% build.causes.each() { cause -> %> ${cause.shortDescription} <% } %></TD></TR>
</TABLE>
<BR/>
<!-- CHANGE SET -->
<% def changeSets = build.changeSets if(changeSets != null) { def hadChanges = false %>
<TABLE width="100%">
<TR><TD class="bg1" colspan="2"><B>CHANGES</B></TD></TR>
<% changeSets.each() { cs_list -> cs_list.each() { cs -> hadChanges = true %>
<TR>
<TD colspan="2" class="bg2"> Revision <B><%= cs.metaClass.hasProperty('commitId') ? cs.commitId : cs.metaClass.hasProperty('revision') ? cs.revision : cs.metaClass.hasProperty('changeNumber') ? cs.changeNumber : "" %></B> by
<B><%= cs.author %>: </B>
<B>(${cs.msgAnnotated})</B>
</TD>
</TR>
<% cs.affectedFiles.each() { p -> %>
<TR>
<TD width="10%"> ${p.editType.name}</TD>
<TD>${p.path}</TD>
</TR>
<% } } } if(!hadChanges) { %>
<TR><TD colspan="2">No Changes</TD></TR>
<% } %>
</TABLE>
<BR/>
<% } %>
<!-- ARTIFACTS -->
<% def artifacts = build.artifacts if(artifacts != null && artifacts.size() > 0) { %>
<TABLE width="100%">
<TR><TD class="bg1"><B>BUILD ARTIFACTS</B></TD></TR>
<TR>
<TD>
<% artifacts.each() { f -> %>
<li>
<a href="${rooturl}${build.url}artifact/${f}">${f}</a>
</li>
<% } %>
</TD>
</TR>
</TABLE>
<BR/>
<% } %>
<!-- MAVEN ARTIFACTS -->
<% try { def mbuilds = build.moduleBuilds if(mbuilds != null) { %>
<TABLE width="100%">
<TR><TD class="bg1"><B>BUILD ARTIFACTS</B></TD></TR>
<% try { mbuilds.each() { m -> %>
<TR><TD class="bg2"><B>${m.key.displayName}</B></TD></TR>
<% m.value.each() { mvnbld -> def artifactz = mvnbld.artifacts if(artifactz != null && artifactz.size() > 0) { %>
<TR>
<TD>
<% artifactz.each() { f -> %>
<li>
<a href="${rooturl}${mvnbld.url}artifact/${f}">${f}</a>
</li>
<% } %>
</TD>
</TR>
<% } } } } catch(e) { // we don't do anything } %>
</TABLE>
<BR/>
<% } }catch(e) { // we don't do anything } %>
<!-- JUnit TEMPLATE -->
<% def junitResultList = it.JUnitTestResult try { def cucumberTestResultAction = it.getAction("org.jenkinsci.plugins.cucumber.jsontestsupport.CucumberTestResultAction") junitResultList.add(cucumberTestResultAction.getResult()) } catch(e) { //cucumberTestResultAction not exist in this build } if (junitResultList.size() > 0) { %>
<TABLE width="100%">
<TR><TD class="bg1" colspan="2"><B>${junitResultList.first().displayName}</B></TD></TR>
<% junitResultList.each{ junitResult -> %>
<% junitResult.getChildren().each { packageResult -> %>
<TR><TD class="bg2" colspan="2"> Name: ${packageResult.getName()} Failed: ${packageResult.getFailCount()} test(s), Passed: ${packageResult.getPassCount()} test(s), Skipped: ${packageResult.getSkipCount()} test(s), Total: ${packageResult.getPassCount()+packageResult.getFailCount()+packageResult.getSkipCount()} test(s)</TD></TR>
<% packageResult.getFailedTests().each{ failed_test -> %>
<TR bgcolor="white"><TD class="test_failed" colspan="2"><B><li>Failed: ${failed_test.getFullName()} </li></B></TD></TR>
<% } } } %>
</TABLE>
<BR/>
<% } %>
<!-- CONSOLE OUTPUT -->
<% if(build.result==hudson.model.Result.FAILURE) { %>
<TABLE width="100%" cellpadding="0" cellspacing="0">
<TR><TD class="bg1"><B>CONSOLE OUTPUT</B></TD></TR>
<% build.getLog(100).each() { line -> %>
<TR><TD class="console">${org.apache.commons.lang.StringEscapeUtils.escapeHtml(line)}</TD></TR>
<% } %>
</TABLE>
<BR/>
<% } %>
</BODY>
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
- 31
- 32
- 33
- 34
- 35
- 36
- 37
- 38
- 39
- 40
- 41
- 42
- 43
- 44
- 45
- 46
- 47
- 48
- 49
- 50
- 51
- 52
- 53
- 54
- 55
- 56
- 57
- 58
- 59
- 60
- 61
- 62
- 63
- 64
- 65
- 66
- 67
- 68
- 69
- 70
- 71
- 72
- 73
- 74
- 75
- 76
- 77
- 78
- 79
- 80
- 81
- 82
- 83
- 84
- 85
- 86
- 87
- 88
- 89
- 90
- 91
- 92
- 93
- 94
- 95
- 96
- 97
- 98
- 99
- 100
- 101
- 102
- 103
- 104
- 105
- 106
- 107
- 108
- 109
- 110
- 111
- 112
- 113
- 114
- 115
- 116
- 117
- 118
- 119
- 120
- 121
- 122
- 123
- 124
- 125
- 126
- 127
- 128
- 129
- 130
- 131
- 132
- 133
- 134
- 135
- 136
- 137
- 138
- 139
- 140
- 141
- 142
- 143
- 144
- 145
- 146
- 147
- 148
- 149
- 150
- 151
- 152
- 153
- 154
- 155
- 156
之后把Default Content
這一欄改為:
${SCRIPT, template="testy.template"}
- 1
就可以了!
可以使用Email Template Testing
這個功能進行測試,把模板名稱輸入進去就可以啦!
假設你輸入groovy-html.template
,即使你的email-templates
文件夾里壓根沒有這個文件,也是能成功的,這是因為該插件默認內置的就是這個模板!