jenkins_api_client 0.6.2 → 0.7.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (40) hide show
  1. data/.gitignore +3 -0
  2. data/.jenkins.yml +9 -0
  3. data/.travis.yml +11 -15
  4. data/CHANGELOG.md +15 -0
  5. data/Gemfile +2 -2
  6. data/README.md +7 -9
  7. data/Rakefile +27 -14
  8. data/lib/jenkins_api_client.rb +36 -6
  9. data/lib/jenkins_api_client/build_queue.rb +213 -0
  10. data/lib/jenkins_api_client/cli/base.rb +10 -6
  11. data/lib/jenkins_api_client/cli/helper.rb +13 -4
  12. data/lib/jenkins_api_client/cli/job.rb +6 -9
  13. data/lib/jenkins_api_client/cli/node.rb +6 -4
  14. data/lib/jenkins_api_client/cli/system.rb +2 -1
  15. data/lib/jenkins_api_client/client.rb +31 -25
  16. data/lib/jenkins_api_client/job.rb +248 -95
  17. data/lib/jenkins_api_client/node.rb +128 -10
  18. data/lib/jenkins_api_client/system.rb +4 -2
  19. data/lib/jenkins_api_client/version.rb +2 -2
  20. data/lib/jenkins_api_client/view.rb +17 -4
  21. data/scripts/login_with_irb.rb +4 -3
  22. data/spec/func_tests/client_spec.rb +90 -0
  23. data/spec/func_tests/job_spec.rb +348 -0
  24. data/spec/func_tests/node_spec.rb +174 -0
  25. data/spec/{spec_helper.rb → func_tests/spec_helper.rb} +2 -2
  26. data/spec/func_tests/system_spec.rb +55 -0
  27. data/spec/func_tests/view_spec.rb +53 -0
  28. data/spec/unit_tests/client_spec.rb +211 -0
  29. data/spec/unit_tests/fixtures/files/computer_sample.xml +17 -0
  30. data/spec/unit_tests/fixtures/files/job_sample.xml +16 -0
  31. data/spec/unit_tests/job_spec.rb +355 -0
  32. data/spec/unit_tests/node_spec.rb +192 -0
  33. data/spec/unit_tests/spec_helper.rb +8 -0
  34. data/spec/unit_tests/system_spec.rb +54 -0
  35. data/spec/unit_tests/view_spec.rb +127 -0
  36. metadata +34 -23
  37. data/spec/client_spec.rb +0 -52
  38. data/spec/job_spec.rb +0 -158
  39. data/spec/node_spec.rb +0 -48
  40. data/spec/system_spec.rb +0 -46
@@ -0,0 +1,17 @@
1
+ <slave>
2
+ <name>slave</name>
3
+ <description/>
4
+ <remoteFS>/var/jenkins</remoteFS>
5
+ <numExecutors>20</numExecutors>
6
+ <mode>NORMAL</mode>
7
+ <retentionStrategy class="hudson.slaves.RetentionStrategy$Always"/>
8
+ <launcher class="hudson.plugins.sshslaves.SSHLauncher" plugin="ssh-slaves@0.21">
9
+ <host>127.0.0.1</host>
10
+ <port>22</port>
11
+ <password>supersecret</password>
12
+ <privatekey>/root/.ssh/api_user_key</privatekey>
13
+ </launcher>
14
+ <label>slave</label>
15
+ <nodeProperties/>
16
+ <userId>kannan</userId>
17
+ </slave>
@@ -0,0 +1,16 @@
1
+ <project>
2
+ <actions/>
3
+ <description/>
4
+ <keepDependencies>false</keepDependencies>
5
+ <properties/>
6
+ <scm class="hudson.scm.NullSCM"/>
7
+ <canRoam>true</canRoam>
8
+ <disabled>false</disabled>
9
+ <blockBuildWhenDownstreamBuilding>false</blockBuildWhenDownstreamBuilding>
10
+ <blockBuildWhenUpstreamBuilding>false</blockBuildWhenUpstreamBuilding>
11
+ <triggers class="vector"/>
12
+ <concurrentBuild>false</concurrentBuild>
13
+ <builders/>
14
+ <publishers/>
15
+ <buildWrappers/>
16
+ </project>
@@ -0,0 +1,355 @@
1
+ require File.expand_path('../spec_helper', __FILE__)
2
+ require 'net/http'
3
+
4
+ describe JenkinsApi::Client::Job do
5
+ context "With properly initialized Client and all methods defined" do
6
+
7
+ before do
8
+ @client = mock
9
+ @job = JenkinsApi::Client::Job.new(@client)
10
+ @sample_json_response = {
11
+ "jobs" => [
12
+ {"name" => "test_job"},
13
+ {"name" => "test_job2"}
14
+ ]
15
+ }
16
+ @sample_json_job_response = {
17
+ "downstreamProjects" => ["test_job1"],
18
+ "upstreamProjects" => ["test_job2"],
19
+ "builds" => [],
20
+ "color" => "running",
21
+ "nextBuildNumber" => 2
22
+ }
23
+ @sample_job_xml = File.read(
24
+ File.expand_path('../fixtures/files/job_sample.xml', __FILE__))
25
+ end
26
+
27
+ describe "InstanceMethods" do
28
+
29
+ describe "#create_job" do
30
+ it "accepts job_name and xml and creates the job" do
31
+ job_name = 'test_job'
32
+ xml = '<name>somename</name>'
33
+ @client.should_receive(:post_config)
34
+ @job.create(job_name, xml)
35
+ end
36
+ end
37
+
38
+ describe "#create_freestyle" do
39
+ it "creates a simple freestyle job" do
40
+ params = {
41
+ :name => 'test_job_using_params'
42
+ }
43
+ @client.should_receive(:post_config)
44
+ @job.create_freestyle(params)
45
+ end
46
+ it "creates a freestyle job with shell command" do
47
+ params = {
48
+ :name => "test_job_using_params_shell",
49
+ :shell_command => "echo this is a freestyle project"
50
+ }
51
+ @client.should_receive(:post_config)
52
+ @job.create_freestyle(params)
53
+ end
54
+ it "accepts Git SCM provider" do
55
+ params = {
56
+ :name => "test_job_using_params_git",
57
+ :scm_provider => "git",
58
+ :scm_url => "git://github.com/arangamani/jenkins_api_client/git",
59
+ :scm_branch => "master"
60
+ }
61
+ @client.should_receive(:post_config)
62
+ @job.create_freestyle(params)
63
+ end
64
+ it "accepts subversion SCM provider" do
65
+ params = {
66
+ :name => "test_job_using_params_subversion",
67
+ :scm_provider => "subversion",
68
+ :scm_url => "http://svn.freebsd.org/base",
69
+ :scm_branch => "master"
70
+ }
71
+ @client.should_receive(:post_config)
72
+ @job.create_freestyle(params)
73
+ end
74
+ it "accepts CVS SCM provider with branch" do
75
+ params = {
76
+ :name => "test_job_using_params_cvs_branch",
77
+ :scm_provider => "cvs",
78
+ :scm_url => "http://cvs.NetBSD.org",
79
+ :scm_module => "src",
80
+ :scm_branch => "MAIN"
81
+ }
82
+ @client.should_receive(:post_config)
83
+ @job.create_freestyle(params)
84
+ end
85
+ it "accepts CVS SCM provider with tag" do
86
+ params = {
87
+ :name => "test_job_using_params_cvs_tag",
88
+ :scm_provider => "cvs",
89
+ :scm_url => "http://cvs.NetBSD.org",
90
+ :scm_module => "src",
91
+ :scm_tag => "MAIN"
92
+ }
93
+ @client.should_receive(:post_config)
94
+ @job.create_freestyle(params)
95
+ end
96
+ end
97
+
98
+ describe "#delete" do
99
+ it "accepts the job name and deletes the job" do
100
+ @client.should_receive(:api_post_request)
101
+ @job.delete('test_job')
102
+ end
103
+ end
104
+
105
+ describe "#stop_build" do
106
+ it "accepts the job name and build number and stops the build" do
107
+ @client.should_receive(:api_get_request).twice.and_return(
108
+ "building" => true, "nextBuildNumber" => 2)
109
+ @client.should_receive(:api_post_request)
110
+ @job.stop_build('test_job')
111
+ end
112
+ end
113
+
114
+ describe "#get_console_output" do
115
+ it "accepts the job name and the obtains the console output" do
116
+ @client.should_receive(:api_get_request).and_return(
117
+ Net::HTTP.get_response(URI('http://example.com/index.html')))
118
+ @job.get_console_output('test_job', 1, 0, 'text')
119
+ end
120
+
121
+ it "raises an error if invalid mode is specified" do
122
+ expect(
123
+ lambda do
124
+ @job.get_console_output('test_job', 1, 0, 'image')
125
+ end
126
+ ).to raise_error
127
+ end
128
+ end
129
+
130
+ describe "#list_all" do
131
+ it "accepts no parameters and returns all jobs in an array" do
132
+ @client.should_receive(:api_get_request).and_return(
133
+ @sample_json_response)
134
+ response = @job.list_all
135
+ response.class.should == Array
136
+ response.size.should == @sample_json_response["jobs"].size
137
+ end
138
+ end
139
+
140
+ describe "#exists?" do
141
+ it "accepts a job name and returns true if the job exists" do
142
+ @client.should_receive(:api_get_request).and_return(
143
+ @sample_json_response)
144
+ @job.exists?("test_job").should == true
145
+ end
146
+ end
147
+
148
+ describe "#list_by_status" do
149
+ it "accepts the status and returns jobs in specified status" do
150
+ @client.should_receive(:api_get_request).twice.and_return(
151
+ @sample_json_response)
152
+ @job.list_by_status("success").class.should == Array
153
+ end
154
+ it "accepts the status and returns the jobs in specified status" do
155
+ @client.should_receive(:api_get_request).and_return(
156
+ @sample_json_response)
157
+ @job.list_by_status("success", ["test_job"]).class.should == Array
158
+ end
159
+ end
160
+
161
+ describe "#list" do
162
+ it "accepts a filter and returns all jobs matching the filter" do
163
+ @client.should_receive(:api_get_request).and_return(
164
+ "jobs" => ["test_job"])
165
+ @job.list("filter").class.should == Array
166
+ end
167
+ end
168
+
169
+ describe "#list_all_with_details" do
170
+ it "accepts no parameters and returns all jobs with details" do
171
+ @client.should_receive(:api_get_request).and_return(
172
+ @sample_json_response)
173
+ response = @job.list_all_with_details
174
+ response.class.should == Array
175
+ response.size.should == @sample_json_response["jobs"].size
176
+ end
177
+ end
178
+
179
+ describe "#list_details" do
180
+ it "accepts the job name and returns its details" do
181
+ @client.should_receive(:api_get_request).and_return(
182
+ @sample_json_response)
183
+ response = @job.list_details("test_job")
184
+ response.class.should == Hash
185
+ end
186
+ end
187
+
188
+ describe "#get_upstream_projects" do
189
+ it "accepts the job name and returns its upstream projects" do
190
+ @client.should_receive(:api_get_request).and_return(
191
+ @sample_json_job_response)
192
+ response = @job.get_upstream_projects("test_job")
193
+ response.class.should == Array
194
+ end
195
+ end
196
+
197
+ describe "#get_downstream_projects" do
198
+ it "accepts the job name and returns its downstream projects" do
199
+ @client.should_receive(:api_get_request).and_return(
200
+ @sample_json_job_response)
201
+ response = @job.get_downstream_projects("test_job")
202
+ response.class.should == Array
203
+ end
204
+ end
205
+
206
+ describe "#get_builds" do
207
+ it "accepts the job name and returns its builds" do
208
+ @client.should_receive(:api_get_request).and_return(
209
+ @sample_json_job_response)
210
+ response = @job.get_builds("test_job")
211
+ response.class.should == Array
212
+ end
213
+ end
214
+
215
+ describe "#color_to_status" do
216
+ it "accepts the color and convert it to correct status" do
217
+ @job.color_to_status("blue").should == "success"
218
+ @job.color_to_status("blue_anime").should == "running"
219
+ @job.color_to_status("red").should == "failure"
220
+ @job.color_to_status("red_anime").should == "running"
221
+ @job.color_to_status("yellow").should == "unstable"
222
+ @job.color_to_status("yellow_anime").should == "running"
223
+ @job.color_to_status("grey").should == "not_run"
224
+ @job.color_to_status("grey_anime").should == "running"
225
+ @job.color_to_status("aborted").should == "aborted"
226
+ end
227
+ it "returns invalid as the output if unknown color is detected" do
228
+ @job.color_to_status("orange").should == "invalid"
229
+ end
230
+ end
231
+
232
+ describe "#get_current_build_status" do
233
+ it "accepts the job name and returns its current build status" do
234
+ @client.should_receive(:api_get_request).and_return(
235
+ @sample_json_job_response)
236
+ @job.get_current_build_status("test_job").class.should == String
237
+ end
238
+ end
239
+
240
+ describe "#get_current_build_number" do
241
+ it "accepts the job name and returns its current build number" do
242
+ @client.should_receive(:api_get_request).and_return(
243
+ @sample_json_job_response)
244
+ @job.get_current_build_number("test_job").class.should == Fixnum
245
+ end
246
+ end
247
+
248
+ describe "#build" do
249
+ it "accepts the job name and builds the job" do
250
+ @client.should_receive(:api_post_request).with(
251
+ "/job/test_job/build").and_return(302)
252
+ @job.build("test_job").should == 302
253
+ end
254
+ end
255
+
256
+ describe "#get_config" do
257
+ it "accepts the job name and obtains its config.xml" do
258
+ @client.should_receive(:get_config).with(
259
+ "/job/test_job").and_return("<job>test_job</job>")
260
+ @job.get_config("test_job").should == "<job>test_job</job>"
261
+ end
262
+ end
263
+
264
+ describe "#post_config" do
265
+ it "accepts the job name and posts its config.xml to the server" do
266
+ @client.should_receive(:post_config).with(
267
+ "/job/test_job/config.xml", "<job>test_job</job>")
268
+ @job.post_config("test_job", "<job>test_job</job>")
269
+ end
270
+ end
271
+
272
+ describe "#change_description" do
273
+ it "accepts the job name and description and changes it" do
274
+ @client.should_receive(:get_config).with(
275
+ "/job/test_job").and_return(@sample_job_xml)
276
+ @client.should_receive(:post_config)
277
+ @job.change_description("test_job", "new description")
278
+ end
279
+ end
280
+
281
+ describe "#block_build_when_downstream_building" do
282
+ it "accepts the job name and blocks build when downstream builds" do
283
+ @client.should_receive(:get_config).with(
284
+ "/job/test_job").and_return(@sample_job_xml)
285
+ @client.should_receive(:post_config)
286
+ @job.block_build_when_downstream_building("test_job")
287
+ end
288
+ end
289
+
290
+ describe "#unblock_build_when_downstream_building" do
291
+ it "accepts the job name and unblocks build when downstream builds" do
292
+ @client.should_receive(:get_config).with(
293
+ "/job/test_job").and_return(@sample_job_xml)
294
+ @job.unblock_build_when_downstream_building("test_job")
295
+ end
296
+ end
297
+
298
+ describe "#block_build_when_upstream_building" do
299
+ it "accepts the job name and blocks build when upstream is building" do
300
+ @client.should_receive(:get_config).with(
301
+ "/job/test_job").and_return(@sample_job_xml)
302
+ @client.should_receive(:post_config)
303
+ @job.block_build_when_upstream_building("test_job")
304
+ end
305
+ end
306
+
307
+ describe "#unblock_build_when_upstream_building" do
308
+ it "accepts the job name and unblocks build when upstream builds" do
309
+ @client.should_receive(:get_config).with(
310
+ "/job/test_job").and_return(@sample_job_xml)
311
+ @job.unblock_build_when_upstream_building("test_job")
312
+ end
313
+ end
314
+
315
+ describe "#execute_concurrent_builds" do
316
+ it "accepts the job name and option and executes concurrent builds" do
317
+ @client.should_receive(:get_config).with(
318
+ "/job/test_job").and_return(@sample_job_xml)
319
+ @client.should_receive(:post_config)
320
+ @job.execute_concurrent_builds("test_job", true)
321
+ end
322
+ end
323
+
324
+ describe "#restrict_to_node" do
325
+ it "accepts the job name and node name and restricts the job node" do
326
+ @client.should_receive(:get_config).with(
327
+ "/job/test_job").and_return(@sample_job_xml)
328
+ @client.should_receive(:post_config)
329
+ @job.restrict_to_node("test_job", "test_slave")
330
+ end
331
+ end
332
+
333
+ describe "#unchain" do
334
+ it "accepts the job names and unchains them" do
335
+ @client.should_receive(:debug).and_return(false)
336
+ @client.should_receive(:get_config).with(
337
+ "/job/test_job").and_return(@sample_job_xml)
338
+ @client.should_receive(:post_config)
339
+ @job.unchain(["test_job"])
340
+ end
341
+ end
342
+
343
+ describe "#chain" do
344
+ it "accepts the job names and other options and chains them" do
345
+ @client.should_receive(:debug).and_return(false)
346
+ @client.should_receive(:get_config).with(
347
+ "/job/test_job").and_return(@sample_job_xml)
348
+ @client.should_receive(:post_config)
349
+ @job.unchain(["test_job"])
350
+ end
351
+ end
352
+
353
+ end
354
+ end
355
+ end
@@ -0,0 +1,192 @@
1
+ require File.expand_path('../spec_helper', __FILE__)
2
+
3
+ describe JenkinsApi::Client::Node do
4
+ context "With properly initialized Client" do
5
+ before do
6
+ @client = mock
7
+ @node = JenkinsApi::Client::Node.new(@client)
8
+ @sample_json_computer_response = {
9
+ "computer" => [
10
+ "displayName" => "slave"
11
+ ]
12
+ }
13
+ computer_sample_xml_filename = '../fixtures/files/computer_sample.xml'
14
+ @sample_computer_xml = File.read(
15
+ File.expand_path(computer_sample_xml_filename , __FILE__)
16
+ )
17
+ end
18
+
19
+ describe "InstanceMethods" do
20
+
21
+ describe "#initialize" do
22
+ it "initializes by receiving an instance of client object" do
23
+ expect(
24
+ lambda{ JenkinsApi::Client::Node.new(@client) }
25
+ ).not_to raise_error
26
+ end
27
+ end
28
+
29
+ describe "#create_dump_slave" do
30
+ it "creates a dump slave by accepting required params" do
31
+ @client.should_receive(
32
+ :api_get_request
33
+ ).with(
34
+ "/computer"
35
+ ).and_return(
36
+ @sample_json_computer_response
37
+ )
38
+ @client.should_receive(:api_post_request).and_return("302")
39
+ @node.create_dump_slave(
40
+ :name => "test_slave",
41
+ :slave_host => "10.10.10.10",
42
+ :private_key_file => "/root/.ssh/id_rsa"
43
+ )
44
+ end
45
+ it "fails if name is not given" do
46
+ expect(
47
+ lambda{
48
+ @node.create_dump_slave(
49
+ :slave_host => "10.10.10.10",
50
+ :private_key_file => "/root/.ssh/id_rsa"
51
+ )
52
+ }
53
+ ).to raise_error
54
+ end
55
+ it "fails if slave_host is not given" do
56
+ expect(
57
+ lambda{
58
+ @node.create_dump_slave(
59
+ :name => "test_slave",
60
+ :private_key_file => "/root/.ssh/id_rsa"
61
+ )
62
+ }
63
+ ).to raise_error
64
+ end
65
+ it "fails if private_key_file is not given" do
66
+ expect(
67
+ lambda{
68
+ @node.create_dump_slave(
69
+ :name => "test_slave",
70
+ :slave_host => "10.10.10.10"
71
+ )
72
+ }
73
+ ).to raise_error
74
+ end
75
+ end
76
+
77
+ describe "#delete" do
78
+ it "gets the node name and deletes if exists" do
79
+ slave_name = "slave"
80
+ @client.should_receive(
81
+ :api_get_request
82
+ ).with(
83
+ "/computer"
84
+ ).and_return(
85
+ @sample_json_computer_response
86
+ )
87
+ @client.should_receive(
88
+ :api_post_request
89
+ ).with(
90
+ "/computer/#{slave_name}/doDelete"
91
+ ).and_return(
92
+ "302"
93
+ )
94
+ @node.delete(slave_name).to_i.should == 302
95
+ end
96
+ it "fails if the given node doesn't exist in Jenkins" do
97
+ slave_name = "not_there"
98
+ @client.should_receive(
99
+ :api_get_request
100
+ ).with(
101
+ "/computer"
102
+ ).and_return(
103
+ @sample_json_computer_response
104
+ )
105
+ expect(
106
+ lambda{ @node.delete(slave_name) }
107
+ ).to raise_error
108
+ end
109
+ end
110
+
111
+ describe "#list" do
112
+ it "accepts filter and lists all nodes matching the filter" do
113
+ @client.should_receive(
114
+ :api_get_request
115
+ ).and_return(
116
+ @sample_json_computer_response
117
+ )
118
+ @node.list("slave").class.should == Array
119
+ end
120
+ end
121
+
122
+ describe "GeneralAttributes" do
123
+ general_attributes = JenkinsApi::Client::Node::GENERAL_ATTRIBUTES
124
+ general_attributes.each do |attribute|
125
+ describe "#get_#{attribute}" do
126
+ it "should get the #{attribute} attribute" do
127
+ @client.should_receive(
128
+ :api_get_request
129
+ ).and_return(
130
+ @sample_json_computer_response
131
+ )
132
+ @node.method("get_#{attribute}").call
133
+ end
134
+ end
135
+ end
136
+ end
137
+
138
+ describe "NodeProperties" do
139
+ node_properties = JenkinsApi::Client::Node::NODE_PROPERTIES
140
+ node_properties.each do |property|
141
+ describe "#is_#{property}?" do
142
+ it "should get the #{property} property" do
143
+ @client.should_receive(
144
+ :api_get_request
145
+ ).twice.and_return(
146
+ @sample_json_computer_response
147
+ )
148
+ @node.method("is_#{property}?").call("slave")
149
+ end
150
+ end
151
+ end
152
+ end
153
+
154
+ describe "NodeAttributes" do
155
+ node_attributes = JenkinsApi::Client::Node::NODE_ATTRIBUTES
156
+ node_attributes.each do |attribute|
157
+ describe "#get_node_#{attribute}" do
158
+ it "should get the #{attribute} node attribute" do
159
+ @client.should_receive(
160
+ :api_get_request
161
+ ).twice.and_return(
162
+ @sample_json_computer_response
163
+ )
164
+ @node.method("get_node_#{attribute}").call("slave")
165
+ end
166
+ end
167
+ end
168
+ end
169
+
170
+ describe "#get_config" do
171
+ it "accepts the node name and obtains the config xml from the server" do
172
+ @client.should_receive(
173
+ :get_config
174
+ ).with(
175
+ "/computer/slave/config.xml"
176
+ ).and_return(
177
+ @sample_computer_xml
178
+ )
179
+ @node.get_config("slave")
180
+ end
181
+ end
182
+
183
+ describe "#post_config" do
184
+ it "accepts the node namd and config.xml and posts it to the server" do
185
+ @client.should_receive(:post_config)
186
+ @node.post_config("slave", @sample_computer_xml)
187
+ end
188
+ end
189
+
190
+ end
191
+ end
192
+ end