Во время работы над докладом « Написание плагина Hudson / Jenkins» (для EclipseCon NA 2014) я хотел публиковать в блоге сообщения об идеях, упомянутых в докладе; в этом посте я объясню, как вы можете взаимодействовать с сервером CI без использования веб-интерфейса.
Удаленный API Jenkins / Hudson может быть очень удобным для быстрого получения статуса работы (и даже для создания или запуска вакансий! Но я не буду освещать этот аспект в этой записи в блоге); давайте посмотрим на некоторые примеры.
Посмотрите на CLI для автоматизации задач конфигурации Jenkins.
Он доступен по адресу http: // hudson-or-jenkins / cli: загрузите hudson-cli.jar или jenkins-cli.jar и начните с этой первой команды:
1
|
$ java -jar jenkins-cli.jar -s http: //jenkins.terracotta.eur.ad.sag:8080/ help |
Недавно мне пришлось заменить 50 заданий матричным заданием: после того, как я создал задание матрицы, мы решили деактивировать предыдущие 50 заданий (прежде чем удалить их навсегда).
Используя CLI, я мог быстро войти:
1
|
$ java -jar jenkins-cli.jar -s http: //jenkins.xx:8080/ login --username anthony --password password |
затем получить список вакансий:
1
|
$ java -jar jenkins-cli.jar -s http: //jenkins.xx:8080/ list-jobs |
Я сохранил список из 50 заданий, которые я хотел деактивировать, в текстовом файле, и перебрал этот список:
1
|
$ while read p; do java -jar jenkins-cli.jar -s http: //jenkins.xx:8080/ disable-job $p; done < list_of_jobs.txt |
Более эффективно, чем через пользовательский интерфейс, не так ли?
Каждый URL может быть представлен как XML или JSON
Как объясняется в документации Jenkins и документации Hudson , вам просто нужно добавить / api / xml или / api / json или / api / python к любому URL-адресу Jenkins, чтобы увидеть соответствующее представление
Вы можете настроить ответы, добавив несколько аргументов в URL:
глубина
Глубина по умолчанию равна 0, чтобы получить более подробную информацию о ваших работах, сборках и т. Д., Установите глубину 1: http://ci.jruby.org/api/xml?depth=1
Этот аргумент может быть вредным для вашего CI-сервера, если он больше 1 (он намного превышает 1 …), поскольку ответы, как правило, становятся действительно большими.
дерево
Аргумент дерева позволяет выбрать часть ответа http://ci.jruby.org/api/xml?depth=1&tree=jobs[displayName,lastBuild[result]]
xpath и exclude (только XML)
Эти аргументы, вероятно, самые мощные, к сожалению, они доступны только для ответов XML:
Если я хочу отображать только неуспешные задания, я могу просто использовать этот URL-адрес: http://ci.jruby.org/api/xml?depth=1&tree=jobs[displayName,lastBuild[result]]&exclude=hudson/ работа [lastBuild [результат = ‘УСПЕХ’]]
И если я хочу видеть только задания с именем, начинающимся с «jruby», я могу применить функции Xpath к URL: http://ci.jruby.org/api/xml?xpath=hudson/job [начинается с (( имя, ‘JRuby’)] & обертка = mywrap
URL-адреса нескольких открытых экземпляров Jenkins и Hudson
Довольно легко найти некоторые общедоступные экземпляры Jenkins и Hudson, чтобы потренироваться в вашей последней фильтрации URL (Google для «Hudson Dashboard» или «Jenkins Dashboard»), но сложнее найти актуальные и значимые (несколько рабочих мест) экземпляры:
Дженкинс:
Хадсон:
- http://deadlock.netbeans.org/hudson/
- https://hudson.eclipse.org/hudson/
- https://hudson.eclipse.org/p2/
Тем не менее, попробуйте сначала ваш местный экземпляр!
Сценарии удаленного API Jenkins и Hudson
Основной интерес удаленного API Jenkins / Hudson заключается в взаимодействии с ним из вашего собственного программного обеспечения: здесь я соберу несколько примеров на нескольких языках сценариев.
Groovy Script для анализа результатов сборки Jenkins Hudson
01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
|
class BuildParser { static void main(String[] args) { if (args.length != 1 ) { println( "Please run the script with a Jenkins or Hudson url as the only argument\n Example : groovy BuildParser.groovy http://ci.jruby.org" ); return ; } def url = args[ 0 ]; def xmlInputFilteringSuccess = new XmlParser().parse(url + "/api/xml?depth=1&tree=jobs[displayName,lastBuild[result]]&exclude=hudson/job[lastBuild[result=%27SUCCESS%27]]" ); def xmlInputNoFilter = new XmlParser().parse(url + "/api/xml?depth=1&tree=jobs" ); def jobs = xmlInputFilteringSuccess.job; println(jobs.size() + " jobs out of " + xmlInputNoFilter.job.size() + " are currently failing" ) jobs.each( { println( it.displayName.text() + " result is " + it.lastBuild.result.text()) } ) } } |
Скрипт Python для анализа результатов сборки Jenkins Hudson
01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
|
import ast import urllib import sys if len(sys.argv) != 2 : print "Please run the script with a Jenkins or Hudson url as the only argument\n Example : python BuildParser.py http://ci.jruby.org" sys.exit( 1 ) url = str(sys.argv[ 1 ]) print url xml_input_no_filter = ast.literal_eval(urllib.urlopen(url + "/api/python?depth=1&tree=jobs[displayName,lastBuild[result]]" ).read()) all_jobs = xml_input_no_filter[ 'jobs' ] non_successful_jobs = [row for row in all_jobs if 'SUCCESS' != row[ 'lastBuild' ][ 'result' ]] print(str(len(non_successful_jobs)) + " jobs out of " + str(len(all_jobs)) + " are currently failing" ) for (i, item) in enumerate(non_successful_jobs): print "Job name : " + item[ 'displayName' ] + "Result : " + item[ 'lastBuild' ][ 'result' ] |
Код JavaScript для анализа результатов сборки Jenkins Hudson
01
02
03
04
05
06
07
08
09
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
|
<!-- Strongly inspired by https: //gist.github.com/alexschwartz/912787 --> <html><head><meta http-equiv= "Content-Type" content= "text/html; charset=ISO-8859-1" > <title>Build Parser</title> <script src= "http://ajax.googleapis.com/ajax/libs/jquery/1.11.0/jquery.min.js" type= "text/javascript" ></script> <script type= "text/javascript" > $(document).ready(function(){ var baseUrl; $( 'button' ).click(function(){ baseUrl = $( "#baseUrl" ).val(); $( "#jobUrl" ).html(baseUrl) var success = function(json) { var allJobs = json[ "jobs" ]; var nonSuccessfulJobs = allJobs.filter(function( job ) { return job[ "lastBuild" ] != null && job[ "lastBuild" ][ "result" ] != "SUCCESS" ; }); $( "#downstream" ).html(nonSuccessfulJobs.length + " out of " + allJobs.length + " are currently failing" ); $.each(nonSuccessfulJobs, function( index, value ) { $( "#downstream" ).append( "<br />Job name : " + value[ "displayName" ] + " : " + value[ "lastBuild" ][ "result" ] ); }); }; $.ajax({ url: baseUrl + "/api/json" , data: "depth=1&tree=jobs[displayName,lastBuild[result]]&jsonp=callBack" , jsonpCallback: "callBack" , dataType: 'jsonp' , success: success }); }); }); </script> </head> <body marginwidth= "50" marginheight= "50" topmargin= "50" leftmargin= "50" > <h3>Input Data</h3> Hudson/Jenkins Base URL: <button>update</button><br /> <h2>Output</h2> <h3>Failing Jobs</h3> <div id= "downstream" > </div> </body></html> |
- Вы можете найти эти скрипты на Github ! Или даже запустите их в вашем браузере для скрипта Javascript Jenkins Hudson Build