blob: 15cb561610ce2a42dfb9dec615f9ac355ae8ba8e [file] [log] [blame]
James E. Blair59fdbac2015-12-07 17:08:06 -08001#!/usr/bin/env python
2
3# Copyright 2012 Hewlett-Packard Development Company, L.P.
4#
5# Licensed under the Apache License, Version 2.0 (the "License"); you may
6# not use this file except in compliance with the License. You may obtain
7# a copy of the License at
8#
9# http://www.apache.org/licenses/LICENSE-2.0
10#
11# Unless required by applicable law or agreed to in writing, software
12# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
13# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
14# License for the specific language governing permissions and limitations
15# under the License.
16
James E. Blaira92cbc82017-01-23 14:56:49 -080017import os
James E. Blair14abdf42015-12-09 16:11:53 -080018import textwrap
James E. Blair59fdbac2015-12-07 17:08:06 -080019
James E. Blairb9c0d772017-03-03 14:34:49 -080020import testtools
21
22import zuul.configloader
James E. Blairbf1a4f22017-03-17 10:59:37 -070023from zuul.lib import encryption
Ricardo Carrillo Cruz22994f92016-12-02 11:41:58 +000024from tests.base import AnsibleZuulTestCase, ZuulTestCase, FIXTURE_DIR
James E. Blair59fdbac2015-12-07 17:08:06 -080025
James E. Blair59fdbac2015-12-07 17:08:06 -080026
James E. Blair3f876d52016-07-22 13:07:14 -070027class TestMultipleTenants(AnsibleZuulTestCase):
James E. Blair59fdbac2015-12-07 17:08:06 -080028 # A temporary class to hold new tests while others are disabled
29
James E. Blair2a629ec2015-12-22 15:32:02 -080030 tenant_config_file = 'config/multi-tenant/main.yaml'
James E. Blair59fdbac2015-12-07 17:08:06 -080031
James E. Blair83005782015-12-11 14:46:03 -080032 def test_multiple_tenants(self):
James E. Blair96f26942015-12-09 10:15:59 -080033 A = self.fake_gerrit.addFakeChange('org/project1', 'master', 'A')
Tobias Henkelbf24fd12017-07-27 06:13:07 +020034 A.addApproval('Code-Review', 2)
35 self.fake_gerrit.addEvent(A.addApproval('Approved', 1))
James E. Blair59fdbac2015-12-07 17:08:06 -080036 self.waitUntilSettled()
James E. Blair96f26942015-12-09 10:15:59 -080037 self.assertEqual(self.getJobFromHistory('project1-test1').result,
James E. Blair59fdbac2015-12-07 17:08:06 -080038 'SUCCESS')
James E. Blair96c6bf82016-01-15 16:20:40 -080039 self.assertEqual(self.getJobFromHistory('python27').result,
40 'SUCCESS')
James E. Blair59fdbac2015-12-07 17:08:06 -080041 self.assertEqual(A.data['status'], 'MERGED')
James E. Blair96f26942015-12-09 10:15:59 -080042 self.assertEqual(A.reported, 2,
43 "A should report start and success")
44 self.assertIn('tenant-one-gate', A.messages[1],
45 "A should transit tenant-one gate")
46 self.assertNotIn('tenant-two-gate', A.messages[1],
47 "A should *not* transit tenant-two gate")
James E. Blair59fdbac2015-12-07 17:08:06 -080048
James E. Blair96f26942015-12-09 10:15:59 -080049 B = self.fake_gerrit.addFakeChange('org/project2', 'master', 'B')
Tobias Henkelbf24fd12017-07-27 06:13:07 +020050 B.addApproval('Code-Review', 2)
51 self.fake_gerrit.addEvent(B.addApproval('Approved', 1))
James E. Blair96f26942015-12-09 10:15:59 -080052 self.waitUntilSettled()
James E. Blair96c6bf82016-01-15 16:20:40 -080053 self.assertEqual(self.getJobFromHistory('python27',
54 'org/project2').result,
55 'SUCCESS')
James E. Blair96f26942015-12-09 10:15:59 -080056 self.assertEqual(self.getJobFromHistory('project2-test1').result,
57 'SUCCESS')
58 self.assertEqual(B.data['status'], 'MERGED')
59 self.assertEqual(B.reported, 2,
60 "B should report start and success")
61 self.assertIn('tenant-two-gate', B.messages[1],
62 "B should transit tenant-two gate")
63 self.assertNotIn('tenant-one-gate', B.messages[1],
64 "B should *not* transit tenant-one gate")
James E. Blair59fdbac2015-12-07 17:08:06 -080065
James E. Blair96f26942015-12-09 10:15:59 -080066 self.assertEqual(A.reported, 2, "Activity in tenant two should"
67 "not affect tenant one")
James E. Blair14abdf42015-12-09 16:11:53 -080068
James E. Blair83005782015-12-11 14:46:03 -080069
James E. Blairff555742017-02-19 11:34:27 -080070class TestInRepoConfig(ZuulTestCase):
James E. Blair83005782015-12-11 14:46:03 -080071 # A temporary class to hold new tests while others are disabled
72
Tobias Henkelabf973e2017-07-28 10:07:34 +020073 config_file = 'zuul-connections-gerrit-and-github.conf'
James E. Blair2a629ec2015-12-22 15:32:02 -080074 tenant_config_file = 'config/in-repo/main.yaml'
James E. Blair83005782015-12-11 14:46:03 -080075
James E. Blair83005782015-12-11 14:46:03 -080076 def test_in_repo_config(self):
James E. Blair14abdf42015-12-09 16:11:53 -080077 A = self.fake_gerrit.addFakeChange('org/project', 'master', 'A')
Tobias Henkelbf24fd12017-07-27 06:13:07 +020078 A.addApproval('Code-Review', 2)
79 self.fake_gerrit.addEvent(A.addApproval('Approved', 1))
James E. Blair14abdf42015-12-09 16:11:53 -080080 self.waitUntilSettled()
81 self.assertEqual(self.getJobFromHistory('project-test1').result,
82 'SUCCESS')
83 self.assertEqual(A.data['status'], 'MERGED')
84 self.assertEqual(A.reported, 2,
85 "A should report start and success")
86 self.assertIn('tenant-one-gate', A.messages[1],
87 "A should transit tenant-one gate")
James E. Blairb97ed802015-12-21 15:55:35 -080088
James E. Blair8b1dc3f2016-07-05 16:49:00 -070089 def test_dynamic_config(self):
90 in_repo_conf = textwrap.dedent(
91 """
92 - job:
Tobias Henkelf02cf512017-07-21 22:55:34 +020093 name: project-test1
94
95 - job:
James E. Blair8b1dc3f2016-07-05 16:49:00 -070096 name: project-test2
97
98 - project:
99 name: org/project
100 tenant-one-gate:
101 jobs:
102 - project-test2
103 """)
104
James E. Blairc73c73a2017-01-20 15:15:15 -0800105 in_repo_playbook = textwrap.dedent(
106 """
107 - hosts: all
108 tasks: []
109 """)
110
111 file_dict = {'.zuul.yaml': in_repo_conf,
112 'playbooks/project-test2.yaml': in_repo_playbook}
James E. Blair8b1dc3f2016-07-05 16:49:00 -0700113 A = self.fake_gerrit.addFakeChange('org/project', 'master', 'A',
James E. Blairc73c73a2017-01-20 15:15:15 -0800114 files=file_dict)
Tobias Henkelbf24fd12017-07-27 06:13:07 +0200115 A.addApproval('Code-Review', 2)
116 self.fake_gerrit.addEvent(A.addApproval('Approved', 1))
James E. Blair8b1dc3f2016-07-05 16:49:00 -0700117 self.waitUntilSettled()
James E. Blair8b1dc3f2016-07-05 16:49:00 -0700118 self.assertEqual(A.data['status'], 'MERGED')
119 self.assertEqual(A.reported, 2,
120 "A should report start and success")
121 self.assertIn('tenant-one-gate', A.messages[1],
122 "A should transit tenant-one gate")
James E. Blair646322f2017-01-27 15:50:34 -0800123 self.assertHistory([
124 dict(name='project-test2', result='SUCCESS', changes='1,1')])
125
James E. Blairc2a5ed72017-02-20 14:12:01 -0500126 self.fake_gerrit.addEvent(A.getChangeMergedEvent())
James E. Blair7bbd7a32017-03-06 11:36:13 -0800127 self.waitUntilSettled()
James E. Blairc2a5ed72017-02-20 14:12:01 -0500128
James E. Blair646322f2017-01-27 15:50:34 -0800129 # Now that the config change is landed, it should be live for
130 # subsequent changes.
131 B = self.fake_gerrit.addFakeChange('org/project', 'master', 'B')
Tobias Henkelbf24fd12017-07-27 06:13:07 +0200132 B.addApproval('Code-Review', 2)
133 self.fake_gerrit.addEvent(B.addApproval('Approved', 1))
James E. Blair646322f2017-01-27 15:50:34 -0800134 self.waitUntilSettled()
135 self.assertEqual(self.getJobFromHistory('project-test2').result,
136 'SUCCESS')
137 self.assertHistory([
138 dict(name='project-test2', result='SUCCESS', changes='1,1'),
139 dict(name='project-test2', result='SUCCESS', changes='2,1')])
James E. Blairc73c73a2017-01-20 15:15:15 -0800140
Tobias Henkelf02cf512017-07-21 22:55:34 +0200141 def test_dynamic_config_non_existing_job(self):
142 """Test that requesting a non existent job fails"""
143 in_repo_conf = textwrap.dedent(
144 """
145 - job:
146 name: project-test1
147
148 - project:
149 name: org/project
150 check:
151 jobs:
152 - non-existent-job
153 """)
154
155 in_repo_playbook = textwrap.dedent(
156 """
157 - hosts: all
158 tasks: []
159 """)
160
161 file_dict = {'.zuul.yaml': in_repo_conf,
162 'playbooks/project-test2.yaml': in_repo_playbook}
163 A = self.fake_gerrit.addFakeChange('org/project', 'master', 'A',
164 files=file_dict)
165 self.fake_gerrit.addEvent(A.getPatchsetCreatedEvent(1))
166 self.waitUntilSettled()
167 self.assertEqual(A.reported, 1,
168 "A should report failure")
169 self.assertEqual(A.patchsets[0]['approvals'][0]['value'], "-1")
170 self.assertIn('Job non-existent-job not defined', A.messages[0],
171 "A should have failed the check pipeline")
172 self.assertHistory([])
173
174 def test_dynamic_config_non_existing_job_in_template(self):
175 """Test that requesting a non existent job fails"""
176 in_repo_conf = textwrap.dedent(
177 """
178 - job:
179 name: project-test1
180
181 - project-template:
182 name: test-template
183 check:
184 jobs:
185 - non-existent-job
186
187 - project:
188 name: org/project
189 templates:
190 - test-template
191 """)
192
193 in_repo_playbook = textwrap.dedent(
194 """
195 - hosts: all
196 tasks: []
197 """)
198
199 file_dict = {'.zuul.yaml': in_repo_conf,
200 'playbooks/project-test2.yaml': in_repo_playbook}
201 A = self.fake_gerrit.addFakeChange('org/project', 'master', 'A',
202 files=file_dict)
203 self.fake_gerrit.addEvent(A.getPatchsetCreatedEvent(1))
204 self.waitUntilSettled()
205 self.assertEqual(A.reported, 1,
206 "A should report failure")
207 self.assertEqual(A.patchsets[0]['approvals'][0]['value'], "-1")
208 self.assertIn('Job non-existent-job not defined', A.messages[0],
209 "A should have failed the check pipeline")
210 self.assertHistory([])
211
Tobias Henkel0f714002017-06-30 23:30:52 +0200212 def test_dynamic_config_new_patchset(self):
213 self.executor_server.hold_jobs_in_build = True
214
215 tenant = self.sched.abide.tenants.get('tenant-one')
216 check_pipeline = tenant.layout.pipelines['check']
217
218 in_repo_conf = textwrap.dedent(
219 """
220 - job:
Tobias Henkelf02cf512017-07-21 22:55:34 +0200221 name: project-test1
222
223 - job:
Tobias Henkel0f714002017-06-30 23:30:52 +0200224 name: project-test2
225
226 - project:
227 name: org/project
228 check:
229 jobs:
230 - project-test2
231 """)
232
233 in_repo_playbook = textwrap.dedent(
234 """
235 - hosts: all
236 tasks: []
237 """)
238
239 file_dict = {'.zuul.yaml': in_repo_conf,
240 'playbooks/project-test2.yaml': in_repo_playbook}
241 A = self.fake_gerrit.addFakeChange('org/project', 'master', 'A',
242 files=file_dict)
243 self.fake_gerrit.addEvent(A.getPatchsetCreatedEvent(1))
244 self.waitUntilSettled()
245
246 items = check_pipeline.getAllItems()
247 self.assertEqual(items[0].change.number, '1')
248 self.assertEqual(items[0].change.patchset, '1')
249 self.assertTrue(items[0].live)
250
251 in_repo_conf = textwrap.dedent(
252 """
253 - job:
Tobias Henkel0ce7ec62017-07-21 22:50:17 +0200254 name: project-test1
255
256 - job:
Tobias Henkel0f714002017-06-30 23:30:52 +0200257 name: project-test2
258
259 - project:
260 name: org/project
261 check:
262 jobs:
263 - project-test1
264 - project-test2
265 """)
266 file_dict = {'.zuul.yaml': in_repo_conf,
267 'playbooks/project-test2.yaml': in_repo_playbook}
268
269 A.addPatchset(files=file_dict)
270 self.fake_gerrit.addEvent(A.getPatchsetCreatedEvent(2))
271
272 self.waitUntilSettled()
273
274 items = check_pipeline.getAllItems()
275 self.assertEqual(items[0].change.number, '1')
276 self.assertEqual(items[0].change.patchset, '2')
277 self.assertTrue(items[0].live)
278
279 self.executor_server.hold_jobs_in_build = False
Tobias Henkel0ce7ec62017-07-21 22:50:17 +0200280 self.executor_server.release('project-test1')
281 self.waitUntilSettled()
Tobias Henkel0f714002017-06-30 23:30:52 +0200282 self.executor_server.release()
283 self.waitUntilSettled()
284
Tobias Henkel0ce7ec62017-07-21 22:50:17 +0200285 self.assertHistory([
286 dict(name='project-test2', result='ABORTED', changes='1,1'),
287 dict(name='project-test1', result='SUCCESS', changes='1,2'),
288 dict(name='project-test2', result='SUCCESS', changes='1,2')])
289
Jesse Keating78f544a2017-07-13 14:27:40 -0700290 def test_dynamic_dependent_pipeline(self):
291 # Test dynamically adding a project to a
292 # dependent pipeline for the first time
293 self.executor_server.hold_jobs_in_build = True
294
295 tenant = self.sched.abide.tenants.get('tenant-one')
296 gate_pipeline = tenant.layout.pipelines['gate']
297
298 in_repo_conf = textwrap.dedent(
299 """
300 - job:
Tobias Henkelf02cf512017-07-21 22:55:34 +0200301 name: project-test1
302
303 - job:
Jesse Keating78f544a2017-07-13 14:27:40 -0700304 name: project-test2
305
306 - project:
307 name: org/project
308 gate:
309 jobs:
310 - project-test2
311 """)
312
313 in_repo_playbook = textwrap.dedent(
314 """
315 - hosts: all
316 tasks: []
317 """)
318
319 file_dict = {'.zuul.yaml': in_repo_conf,
320 'playbooks/project-test2.yaml': in_repo_playbook}
321 A = self.fake_gerrit.addFakeChange('org/project', 'master', 'A',
322 files=file_dict)
Tobias Henkelbf24fd12017-07-27 06:13:07 +0200323 A.addApproval('Approved', 1)
324 self.fake_gerrit.addEvent(A.addApproval('Code-Review', 2))
Jesse Keating78f544a2017-07-13 14:27:40 -0700325 self.waitUntilSettled()
326
327 items = gate_pipeline.getAllItems()
328 self.assertEqual(items[0].change.number, '1')
329 self.assertEqual(items[0].change.patchset, '1')
330 self.assertTrue(items[0].live)
331
332 self.executor_server.hold_jobs_in_build = False
333 self.executor_server.release()
334 self.waitUntilSettled()
335
336 # Make sure the dynamic queue got cleaned up
337 self.assertEqual(gate_pipeline.queues, [])
338
James E. Blairff555742017-02-19 11:34:27 -0800339 def test_in_repo_branch(self):
340 in_repo_conf = textwrap.dedent(
341 """
342 - job:
Tobias Henkelf02cf512017-07-21 22:55:34 +0200343 name: project-test1
344
345 - job:
James E. Blairff555742017-02-19 11:34:27 -0800346 name: project-test2
347
348 - project:
349 name: org/project
350 tenant-one-gate:
351 jobs:
352 - project-test2
353 """)
354
355 in_repo_playbook = textwrap.dedent(
356 """
357 - hosts: all
358 tasks: []
359 """)
360
361 file_dict = {'.zuul.yaml': in_repo_conf,
362 'playbooks/project-test2.yaml': in_repo_playbook}
363 self.create_branch('org/project', 'stable')
364 A = self.fake_gerrit.addFakeChange('org/project', 'stable', 'A',
365 files=file_dict)
Tobias Henkelbf24fd12017-07-27 06:13:07 +0200366 A.addApproval('Code-Review', 2)
367 self.fake_gerrit.addEvent(A.addApproval('Approved', 1))
James E. Blairff555742017-02-19 11:34:27 -0800368 self.waitUntilSettled()
369 self.assertEqual(A.data['status'], 'MERGED')
370 self.assertEqual(A.reported, 2,
371 "A should report start and success")
372 self.assertIn('tenant-one-gate', A.messages[1],
373 "A should transit tenant-one gate")
374 self.assertHistory([
375 dict(name='project-test2', result='SUCCESS', changes='1,1')])
376 self.fake_gerrit.addEvent(A.getChangeMergedEvent())
James E. Blair7bbd7a32017-03-06 11:36:13 -0800377 self.waitUntilSettled()
James E. Blairff555742017-02-19 11:34:27 -0800378
379 # The config change should not affect master.
380 B = self.fake_gerrit.addFakeChange('org/project', 'master', 'B')
Tobias Henkelbf24fd12017-07-27 06:13:07 +0200381 B.addApproval('Code-Review', 2)
382 self.fake_gerrit.addEvent(B.addApproval('Approved', 1))
James E. Blairff555742017-02-19 11:34:27 -0800383 self.waitUntilSettled()
384 self.assertHistory([
385 dict(name='project-test2', result='SUCCESS', changes='1,1'),
386 dict(name='project-test1', result='SUCCESS', changes='2,1')])
387
388 # The config change should be live for further changes on
389 # stable.
390 C = self.fake_gerrit.addFakeChange('org/project', 'stable', 'C')
Tobias Henkelbf24fd12017-07-27 06:13:07 +0200391 C.addApproval('Code-Review', 2)
392 self.fake_gerrit.addEvent(C.addApproval('Approved', 1))
James E. Blairff555742017-02-19 11:34:27 -0800393 self.waitUntilSettled()
394 self.assertHistory([
395 dict(name='project-test2', result='SUCCESS', changes='1,1'),
396 dict(name='project-test1', result='SUCCESS', changes='2,1'),
397 dict(name='project-test2', result='SUCCESS', changes='3,1')])
398
James E. Blaira5a12492017-05-03 11:40:48 -0700399 def test_crd_dynamic_config_branch(self):
400 # Test that we can create a job in one repo and be able to use
401 # it from a different branch on a different repo.
402
403 self.create_branch('org/project1', 'stable')
404
405 in_repo_conf = textwrap.dedent(
406 """
407 - job:
Tobias Henkelf02cf512017-07-21 22:55:34 +0200408 name: project-test1
409
410 - job:
James E. Blaira5a12492017-05-03 11:40:48 -0700411 name: project-test2
412
413 - project:
414 name: org/project
415 check:
416 jobs:
417 - project-test2
418 """)
419
420 in_repo_playbook = textwrap.dedent(
421 """
422 - hosts: all
423 tasks: []
424 """)
425
426 file_dict = {'.zuul.yaml': in_repo_conf,
427 'playbooks/project-test2.yaml': in_repo_playbook}
428 A = self.fake_gerrit.addFakeChange('org/project', 'master', 'A',
429 files=file_dict)
430
431 second_repo_conf = textwrap.dedent(
432 """
433 - project:
434 name: org/project1
435 check:
436 jobs:
437 - project-test2
438 """)
439
440 second_file_dict = {'.zuul.yaml': second_repo_conf}
441 B = self.fake_gerrit.addFakeChange('org/project1', 'stable', 'B',
442 files=second_file_dict)
443 B.data['commitMessage'] = '%s\n\nDepends-On: %s\n' % (
444 B.subject, A.data['id'])
445
446 self.fake_gerrit.addEvent(A.getPatchsetCreatedEvent(1))
447 self.waitUntilSettled()
448 self.fake_gerrit.addEvent(B.getPatchsetCreatedEvent(1))
449 self.waitUntilSettled()
450
451 self.assertEqual(A.reported, 1, "A should report")
452 self.assertHistory([
453 dict(name='project-test2', result='SUCCESS', changes='1,1'),
454 dict(name='project-test2', result='SUCCESS', changes='1,1 2,1'),
455 ])
456
James E. Blair149b69c2017-03-02 10:48:16 -0800457 def test_untrusted_syntax_error(self):
James E. Blaire53250c2017-03-01 14:34:36 -0800458 in_repo_conf = textwrap.dedent(
459 """
460 - job:
461 name: project-test2
462 foo: error
463 """)
464
465 file_dict = {'.zuul.yaml': in_repo_conf}
466 A = self.fake_gerrit.addFakeChange('org/project', 'master', 'A',
467 files=file_dict)
Tobias Henkelbf24fd12017-07-27 06:13:07 +0200468 A.addApproval('Code-Review', 2)
469 self.fake_gerrit.addEvent(A.addApproval('Approved', 1))
James E. Blaire53250c2017-03-01 14:34:36 -0800470 self.waitUntilSettled()
471
472 self.assertEqual(A.data['status'], 'NEW')
Tobias Henkel9842bd72017-05-16 13:40:03 +0200473 self.assertEqual(A.reported, 1,
474 "A should report failure")
475 self.assertIn('syntax error', A.messages[0],
James E. Blaire53250c2017-03-01 14:34:36 -0800476 "A should have a syntax error reported")
477
James E. Blair149b69c2017-03-02 10:48:16 -0800478 def test_trusted_syntax_error(self):
479 in_repo_conf = textwrap.dedent(
480 """
481 - job:
482 name: project-test2
483 foo: error
484 """)
485
486 file_dict = {'zuul.yaml': in_repo_conf}
487 A = self.fake_gerrit.addFakeChange('common-config', 'master', 'A',
488 files=file_dict)
Tobias Henkelbf24fd12017-07-27 06:13:07 +0200489 A.addApproval('Code-Review', 2)
490 self.fake_gerrit.addEvent(A.addApproval('Approved', 1))
James E. Blair149b69c2017-03-02 10:48:16 -0800491 self.waitUntilSettled()
492
493 self.assertEqual(A.data['status'], 'NEW')
Tobias Henkel9842bd72017-05-16 13:40:03 +0200494 self.assertEqual(A.reported, 1,
495 "A should report failure")
496 self.assertIn('syntax error', A.messages[0],
James E. Blair149b69c2017-03-02 10:48:16 -0800497 "A should have a syntax error reported")
498
James E. Blair6f140c72017-03-03 10:32:07 -0800499 def test_untrusted_yaml_error(self):
500 in_repo_conf = textwrap.dedent(
501 """
502 - job:
503 foo: error
504 """)
505
506 file_dict = {'.zuul.yaml': in_repo_conf}
507 A = self.fake_gerrit.addFakeChange('org/project', 'master', 'A',
508 files=file_dict)
Tobias Henkelbf24fd12017-07-27 06:13:07 +0200509 A.addApproval('Code-Review', 2)
510 self.fake_gerrit.addEvent(A.addApproval('Approved', 1))
James E. Blair6f140c72017-03-03 10:32:07 -0800511 self.waitUntilSettled()
512
513 self.assertEqual(A.data['status'], 'NEW')
Tobias Henkel9842bd72017-05-16 13:40:03 +0200514 self.assertEqual(A.reported, 1,
515 "A should report failure")
516 self.assertIn('syntax error', A.messages[0],
James E. Blair6f140c72017-03-03 10:32:07 -0800517 "A should have a syntax error reported")
518
James E. Blairdb04e6a2017-05-03 14:49:36 -0700519 def test_untrusted_shadow_error(self):
520 in_repo_conf = textwrap.dedent(
521 """
522 - job:
523 name: common-config-test
524 """)
525
526 file_dict = {'.zuul.yaml': in_repo_conf}
527 A = self.fake_gerrit.addFakeChange('org/project', 'master', 'A',
528 files=file_dict)
Tobias Henkelbf24fd12017-07-27 06:13:07 +0200529 A.addApproval('Code-Review', 2)
530 self.fake_gerrit.addEvent(A.addApproval('Approved', 1))
James E. Blairdb04e6a2017-05-03 14:49:36 -0700531 self.waitUntilSettled()
532
533 self.assertEqual(A.data['status'], 'NEW')
Tobias Henkel9842bd72017-05-16 13:40:03 +0200534 self.assertEqual(A.reported, 1,
535 "A should report failure")
536 self.assertIn('not permitted to shadow', A.messages[0],
James E. Blairdb04e6a2017-05-03 14:49:36 -0700537 "A should have a syntax error reported")
538
James E. Blaird5656ad2017-06-02 14:29:41 -0700539 def test_untrusted_pipeline_error(self):
540 in_repo_conf = textwrap.dedent(
541 """
542 - pipeline:
543 name: test
544 """)
545
546 file_dict = {'.zuul.yaml': in_repo_conf}
547 A = self.fake_gerrit.addFakeChange('org/project', 'master', 'A',
548 files=file_dict)
Tobias Henkelbf24fd12017-07-27 06:13:07 +0200549 A.addApproval('Code-Review', 2)
550 self.fake_gerrit.addEvent(A.addApproval('Approved', 1))
James E. Blaird5656ad2017-06-02 14:29:41 -0700551 self.waitUntilSettled()
552
553 self.assertEqual(A.data['status'], 'NEW')
554 self.assertEqual(A.reported, 1,
555 "A should report failure")
556 self.assertIn('Pipelines may not be defined', A.messages[0],
557 "A should have a syntax error reported")
558
559 def test_untrusted_project_error(self):
560 in_repo_conf = textwrap.dedent(
561 """
562 - project:
563 name: org/project1
564 """)
565
566 file_dict = {'.zuul.yaml': in_repo_conf}
567 A = self.fake_gerrit.addFakeChange('org/project', 'master', 'A',
568 files=file_dict)
Tobias Henkelbf24fd12017-07-27 06:13:07 +0200569 A.addApproval('Code-Review', 2)
570 self.fake_gerrit.addEvent(A.addApproval('Approved', 1))
James E. Blaird5656ad2017-06-02 14:29:41 -0700571 self.waitUntilSettled()
572
573 self.assertEqual(A.data['status'], 'NEW')
574 self.assertEqual(A.reported, 1,
575 "A should report failure")
576 self.assertIn('the only project definition permitted', A.messages[0],
577 "A should have a syntax error reported")
578
James E. Blaire64b0e42017-06-08 11:23:34 -0700579 def test_duplicate_node_error(self):
580 in_repo_conf = textwrap.dedent(
581 """
582 - nodeset:
583 name: duplicate
584 nodes:
585 - name: compute
James E. Blair16d96a02017-06-08 11:32:56 -0700586 label: foo
James E. Blaire64b0e42017-06-08 11:23:34 -0700587 - name: compute
James E. Blair16d96a02017-06-08 11:32:56 -0700588 label: foo
James E. Blaire64b0e42017-06-08 11:23:34 -0700589 """)
590
591 file_dict = {'.zuul.yaml': in_repo_conf}
592 A = self.fake_gerrit.addFakeChange('org/project', 'master', 'A',
593 files=file_dict)
Tobias Henkelbf24fd12017-07-27 06:13:07 +0200594 A.addApproval('Code-Review', 2)
595 self.fake_gerrit.addEvent(A.addApproval('Approved', 1))
James E. Blaire64b0e42017-06-08 11:23:34 -0700596 self.waitUntilSettled()
597
598 self.assertEqual(A.data['status'], 'NEW')
599 self.assertEqual(A.reported, 1,
600 "A should report failure")
601 self.assertIn('appears multiple times', A.messages[0],
602 "A should have a syntax error reported")
603
604 def test_duplicate_group_error(self):
605 in_repo_conf = textwrap.dedent(
606 """
607 - nodeset:
608 name: duplicate
609 nodes:
610 - name: compute
James E. Blair16d96a02017-06-08 11:32:56 -0700611 label: foo
James E. Blaire64b0e42017-06-08 11:23:34 -0700612 groups:
613 - name: group
614 nodes: compute
615 - name: group
616 nodes: compute
617 """)
618
619 file_dict = {'.zuul.yaml': in_repo_conf}
620 A = self.fake_gerrit.addFakeChange('org/project', 'master', 'A',
621 files=file_dict)
Tobias Henkelbf24fd12017-07-27 06:13:07 +0200622 A.addApproval('Code-Review', 2)
623 self.fake_gerrit.addEvent(A.addApproval('Approved', 1))
James E. Blaire64b0e42017-06-08 11:23:34 -0700624 self.waitUntilSettled()
625
626 self.assertEqual(A.data['status'], 'NEW')
627 self.assertEqual(A.reported, 1,
628 "A should report failure")
629 self.assertIn('appears multiple times', A.messages[0],
630 "A should have a syntax error reported")
631
James E. Blair09f9ffe2017-07-11 15:30:25 -0700632 def test_multi_repo(self):
633 downstream_repo_conf = textwrap.dedent(
634 """
635 - project:
636 name: org/project1
637 tenant-one-gate:
638 jobs:
639 - project-test1
640
641 - job:
642 name: project1-test1
643 parent: project-test1
644 """)
645
646 file_dict = {'.zuul.yaml': downstream_repo_conf}
647 A = self.fake_gerrit.addFakeChange('org/project1', 'master', 'A',
648 files=file_dict)
Tobias Henkelbf24fd12017-07-27 06:13:07 +0200649 A.addApproval('Code-Review', 2)
650 self.fake_gerrit.addEvent(A.addApproval('Approved', 1))
James E. Blair09f9ffe2017-07-11 15:30:25 -0700651 self.waitUntilSettled()
652
653 self.assertEqual(A.data['status'], 'MERGED')
654 self.fake_gerrit.addEvent(A.getChangeMergedEvent())
655 self.waitUntilSettled()
656
657 upstream_repo_conf = textwrap.dedent(
658 """
659 - job:
660 name: project-test1
661
662 - job:
663 name: project-test2
664
665 - project:
666 name: org/project
667 tenant-one-gate:
668 jobs:
669 - project-test1
670 """)
671
672 file_dict = {'.zuul.yaml': upstream_repo_conf}
673 B = self.fake_gerrit.addFakeChange('org/project', 'master', 'B',
674 files=file_dict)
Tobias Henkelbf24fd12017-07-27 06:13:07 +0200675 B.addApproval('Code-Review', 2)
676 self.fake_gerrit.addEvent(B.addApproval('Approved', 1))
James E. Blair09f9ffe2017-07-11 15:30:25 -0700677 self.waitUntilSettled()
678
679 self.assertEqual(B.data['status'], 'MERGED')
680 self.fake_gerrit.addEvent(B.getChangeMergedEvent())
681 self.waitUntilSettled()
682
683 tenant = self.sched.abide.tenants.get('tenant-one')
684 # Ensure the latest change is reflected in the config; if it
685 # isn't this will raise an exception.
686 tenant.layout.getJob('project-test2')
687
James E. Blairc73c73a2017-01-20 15:15:15 -0800688
689class TestAnsible(AnsibleZuulTestCase):
690 # A temporary class to hold new tests while others are disabled
691
692 tenant_config_file = 'config/ansible/main.yaml'
693
694 def test_playbook(self):
Jamie Lennox7655b552017-03-17 12:33:38 +1100695 # Keep the jobdir around so we can inspect contents if an
696 # assert fails.
697 self.executor_server.keep_jobdir = True
698 # Output extra ansible info so we might see errors.
699 self.executor_server.verbose = True
700 # Add a site variables file, used by check-vars
701 path = os.path.join(FIXTURE_DIR, 'config', 'ansible',
702 'variables.yaml')
703 self.config.set('executor', 'variables', path)
James E. Blairc73c73a2017-01-20 15:15:15 -0800704 A = self.fake_gerrit.addFakeChange('org/project', 'master', 'A')
705 self.fake_gerrit.addEvent(A.getPatchsetCreatedEvent(1))
706 self.waitUntilSettled()
Tobias Henkel077f2f32017-05-30 20:16:46 +0200707 build_timeout = self.getJobFromHistory('timeout')
Jamie Lennox7655b552017-03-17 12:33:38 +1100708 with self.jobLog(build_timeout):
709 self.assertEqual(build_timeout.result, 'TIMED_OUT')
Tobias Henkel077f2f32017-05-30 20:16:46 +0200710 build_faillocal = self.getJobFromHistory('faillocal')
Jamie Lennox7655b552017-03-17 12:33:38 +1100711 with self.jobLog(build_faillocal):
712 self.assertEqual(build_faillocal.result, 'FAILURE')
Tobias Henkel077f2f32017-05-30 20:16:46 +0200713 build_failpost = self.getJobFromHistory('failpost')
Jamie Lennox7655b552017-03-17 12:33:38 +1100714 with self.jobLog(build_failpost):
715 self.assertEqual(build_failpost.result, 'POST_FAILURE')
Tobias Henkel077f2f32017-05-30 20:16:46 +0200716 build_check_vars = self.getJobFromHistory('check-vars')
Jamie Lennox7655b552017-03-17 12:33:38 +1100717 with self.jobLog(build_check_vars):
718 self.assertEqual(build_check_vars.result, 'SUCCESS')
Tobias Henkel077f2f32017-05-30 20:16:46 +0200719 build_hello = self.getJobFromHistory('hello-world')
Jamie Lennox7655b552017-03-17 12:33:38 +1100720 with self.jobLog(build_hello):
721 self.assertEqual(build_hello.result, 'SUCCESS')
Tobias Henkel077f2f32017-05-30 20:16:46 +0200722 build_python27 = self.getJobFromHistory('python27')
Jamie Lennox7655b552017-03-17 12:33:38 +1100723 with self.jobLog(build_python27):
724 self.assertEqual(build_python27.result, 'SUCCESS')
725 flag_path = os.path.join(self.test_root,
726 build_python27.uuid + '.flag')
727 self.assertTrue(os.path.exists(flag_path))
728 copied_path = os.path.join(self.test_root, build_python27.uuid +
729 '.copied')
730 self.assertTrue(os.path.exists(copied_path))
731 failed_path = os.path.join(self.test_root, build_python27.uuid +
732 '.failed')
733 self.assertFalse(os.path.exists(failed_path))
734 pre_flag_path = os.path.join(self.test_root, build_python27.uuid +
735 '.pre.flag')
736 self.assertTrue(os.path.exists(pre_flag_path))
737 post_flag_path = os.path.join(self.test_root, build_python27.uuid +
738 '.post.flag')
739 self.assertTrue(os.path.exists(post_flag_path))
740 bare_role_flag_path = os.path.join(self.test_root,
741 build_python27.uuid +
742 '.bare-role.flag')
743 self.assertTrue(os.path.exists(bare_role_flag_path))
744 secrets_path = os.path.join(self.test_root,
745 build_python27.uuid + '.secrets')
746 with open(secrets_path) as f:
747 self.assertEqual(f.read(), "test-username test-password")
James E. Blairb9c0d772017-03-03 14:34:49 -0800748
Jamie Lennox7655b552017-03-17 12:33:38 +1100749 msg = A.messages[0]
750 success = "{} https://success.example.com/zuul-logs/{}"
751 fail = "{} https://failure.example.com/zuul-logs/{}"
752 self.assertIn(success.format("python27", build_python27.uuid), msg)
753 self.assertIn(fail.format("faillocal", build_faillocal.uuid), msg)
754 self.assertIn(success.format("check-vars",
755 build_check_vars.uuid), msg)
756 self.assertIn(success.format("hello-world", build_hello.uuid), msg)
757 self.assertIn(fail.format("timeout", build_timeout.uuid), msg)
758 self.assertIn(fail.format("failpost", build_failpost.uuid), msg)
Tobias Henkel077f2f32017-05-30 20:16:46 +0200759
James E. Blairabbaa6f2017-04-06 16:11:44 -0700760 def _add_job(self, job_name):
761 conf = textwrap.dedent(
762 """
763 - job:
764 name: %s
765
766 - project:
767 name: org/plugin-project
768 check:
769 jobs:
770 - %s
771 """ % (job_name, job_name))
772
773 file_dict = {'.zuul.yaml': conf}
774 A = self.fake_gerrit.addFakeChange('org/plugin-project', 'master', 'A',
775 files=file_dict)
776 self.fake_gerrit.addEvent(A.getPatchsetCreatedEvent(1))
777 self.waitUntilSettled()
778
779 def test_plugins(self):
780 # Keep the jobdir around so we can inspect contents if an
781 # assert fails.
782 self.executor_server.keep_jobdir = True
783 # Output extra ansible info so we might see errors.
784 self.executor_server.verbose = True
785
786 count = 0
787 plugin_tests = [
788 ('passwd', 'FAILURE'),
789 ('cartesian', 'SUCCESS'),
790 ('consul_kv', 'FAILURE'),
791 ('credstash', 'FAILURE'),
792 ('csvfile_good', 'SUCCESS'),
793 ('csvfile_bad', 'FAILURE'),
794 ]
795 for job_name, result in plugin_tests:
796 count += 1
797 self._add_job(job_name)
798
799 job = self.getJobFromHistory(job_name)
800 with self.jobLog(job):
801 self.assertEqual(count, len(self.history))
802 build = self.history[-1]
803 self.assertEqual(build.result, result)
804
805 # TODOv3(jeblair): parse the ansible output and verify we're
806 # getting the exception we expect.
807
James E. Blairb9c0d772017-03-03 14:34:49 -0800808
James E. Blaira4d4eef2017-06-30 14:49:17 -0700809class TestPrePlaybooks(AnsibleZuulTestCase):
810 # A temporary class to hold new tests while others are disabled
811
812 tenant_config_file = 'config/pre-playbook/main.yaml'
813
814 def test_pre_playbook_fail(self):
815 # Test that we run the post playbooks (but not the actual
816 # playbook) when a pre-playbook fails.
817 A = self.fake_gerrit.addFakeChange('org/project', 'master', 'A')
818 self.fake_gerrit.addEvent(A.getPatchsetCreatedEvent(1))
819 self.waitUntilSettled()
820 build = self.getJobFromHistory('python27')
821 self.assertIsNone(build.result)
822 self.assertIn('RETRY_LIMIT', A.messages[0])
823 flag_path = os.path.join(self.test_root, build.uuid +
824 '.main.flag')
825 self.assertFalse(os.path.exists(flag_path))
826 pre_flag_path = os.path.join(self.test_root, build.uuid +
827 '.pre.flag')
828 self.assertFalse(os.path.exists(pre_flag_path))
829 post_flag_path = os.path.join(self.test_root, build.uuid +
830 '.post.flag')
James E. Blair21037782017-07-19 11:56:55 -0700831 self.assertTrue(os.path.exists(post_flag_path),
832 "The file %s should exist" % post_flag_path)
James E. Blaira4d4eef2017-06-30 14:49:17 -0700833
834
James E. Blairb9c0d772017-03-03 14:34:49 -0800835class TestBrokenConfig(ZuulTestCase):
836 # Test that we get an appropriate syntax error if we start with a
837 # broken config.
838
839 tenant_config_file = 'config/broken/main.yaml'
840
841 def setUp(self):
842 with testtools.ExpectedException(
843 zuul.configloader.ConfigurationSyntaxError,
844 "\nZuul encountered a syntax error"):
845 super(TestBrokenConfig, self).setUp()
846
847 def test_broken_config_on_startup(self):
848 pass
Ricardo Carrillo Cruz22994f92016-12-02 11:41:58 +0000849
850
851class TestProjectKeys(ZuulTestCase):
852 # Test that we can generate project keys
853
854 # Normally the test infrastructure copies a static key in place
855 # for each project before starting tests. This saves time because
856 # Zuul's automatic key-generation on startup can be slow. To make
857 # sure we exercise that code, in this test we allow Zuul to create
858 # keys for the project on startup.
859 create_project_keys = True
Tobias Henkelabf973e2017-07-28 10:07:34 +0200860 config_file = 'zuul-connections-gerrit-and-github.conf'
Ricardo Carrillo Cruz22994f92016-12-02 11:41:58 +0000861 tenant_config_file = 'config/in-repo/main.yaml'
862
863 def test_key_generation(self):
864 key_root = os.path.join(self.state_root, 'keys')
865 private_key_file = os.path.join(key_root, 'gerrit/org/project.pem')
866 # Make sure that a proper key was created on startup
867 with open(private_key_file, "rb") as f:
James E. Blairbf1a4f22017-03-17 10:59:37 -0700868 private_key, public_key = \
869 encryption.deserialize_rsa_keypair(f.read())
Ricardo Carrillo Cruz22994f92016-12-02 11:41:58 +0000870
871 with open(os.path.join(FIXTURE_DIR, 'private.pem')) as i:
872 fixture_private_key = i.read()
873
874 # Make sure that we didn't just end up with the static fixture
875 # key
876 self.assertNotEqual(fixture_private_key, private_key)
877
878 # Make sure it's the right length
879 self.assertEqual(4096, private_key.key_size)
James E. Blairbce76932017-05-04 10:03:15 -0700880
881
James E. Blairbb94dfa2017-07-11 07:45:19 -0700882class RoleTestCase(ZuulTestCase):
James E. Blair1b27f6a2017-07-14 14:09:07 -0700883 def _assertRolePath(self, build, playbook, content):
884 path = os.path.join(self.test_root, build.uuid,
885 'ansible', playbook, 'ansible.cfg')
886 roles_paths = []
887 with open(path) as f:
888 for line in f:
889 if line.startswith('roles_path'):
890 roles_paths.append(line)
891 print(roles_paths)
892 if content:
893 self.assertEqual(len(roles_paths), 1,
894 "Should have one roles_path line in %s" %
895 (playbook,))
896 self.assertIn(content, roles_paths[0])
897 else:
898 self.assertEqual(len(roles_paths), 0,
899 "Should have no roles_path line in %s" %
900 (playbook,))
901
James E. Blairbb94dfa2017-07-11 07:45:19 -0700902
903class TestRoles(RoleTestCase):
904 tenant_config_file = 'config/roles/main.yaml'
905
James E. Blairbce76932017-05-04 10:03:15 -0700906 def test_role(self):
907 # This exercises a proposed change to a role being checked out
908 # and used.
909 A = self.fake_gerrit.addFakeChange('bare-role', 'master', 'A')
910 B = self.fake_gerrit.addFakeChange('org/project', 'master', 'A')
911 B.data['commitMessage'] = '%s\n\nDepends-On: %s\n' % (
912 B.subject, A.data['id'])
913 self.fake_gerrit.addEvent(A.getPatchsetCreatedEvent(1))
914 self.fake_gerrit.addEvent(B.getPatchsetCreatedEvent(1))
915 self.waitUntilSettled()
916 self.assertHistory([
917 dict(name='project-test', result='SUCCESS', changes='1,1 2,1'),
918 ])
James E. Blair6459db12017-06-29 14:57:20 -0700919
James E. Blair1b27f6a2017-07-14 14:09:07 -0700920 def test_role_inheritance(self):
921 self.executor_server.hold_jobs_in_build = True
922 conf = textwrap.dedent(
923 """
924 - job:
925 name: parent
926 roles:
927 - zuul: bare-role
928 pre-run: playbooks/parent-pre
929 post-run: playbooks/parent-post
930
931 - job:
932 name: project-test
933 parent: parent
934 roles:
935 - zuul: org/project
936
937 - project:
938 name: org/project
939 check:
940 jobs:
941 - project-test
942 """)
943
944 file_dict = {'.zuul.yaml': conf}
945 A = self.fake_gerrit.addFakeChange('org/project', 'master', 'A',
946 files=file_dict)
947 self.fake_gerrit.addEvent(A.getPatchsetCreatedEvent(1))
948 self.waitUntilSettled()
949
950 self.assertEqual(len(self.builds), 1)
951 build = self.getBuildByName('project-test')
952 self._assertRolePath(build, 'pre_playbook_0', 'role_0')
953 self._assertRolePath(build, 'playbook_0', 'role_0')
954 self._assertRolePath(build, 'playbook_0', 'role_1')
955 self._assertRolePath(build, 'post_playbook_0', 'role_0')
956
957 self.executor_server.hold_jobs_in_build = False
958 self.executor_server.release()
959 self.waitUntilSettled()
960
961 self.assertHistory([
962 dict(name='project-test', result='SUCCESS', changes='1,1'),
963 ])
964
James E. Blair6f699732017-07-18 14:19:11 -0700965 def test_role_error(self):
966 conf = textwrap.dedent(
967 """
968 - job:
969 name: project-test
970 roles:
971 - zuul: common-config
972
973 - project:
974 name: org/project
975 check:
976 jobs:
977 - project-test
978 """)
979
980 file_dict = {'.zuul.yaml': conf}
981 A = self.fake_gerrit.addFakeChange('org/project', 'master', 'A',
982 files=file_dict)
983 self.fake_gerrit.addEvent(A.getPatchsetCreatedEvent(1))
984 self.waitUntilSettled()
985 self.assertIn(
986 '- project-test project-test : ERROR Unable to find role',
987 A.messages[-1])
988
James E. Blair6459db12017-06-29 14:57:20 -0700989
James E. Blairbb94dfa2017-07-11 07:45:19 -0700990class TestImplicitRoles(RoleTestCase):
991 tenant_config_file = 'config/implicit-roles/main.yaml'
992
993 def test_missing_roles(self):
994 # Test implicit and explicit roles for a project which does
995 # not have roles. The implicit role should be silently
996 # ignored since the project doesn't supply roles, but if a
997 # user declares an explicit role, it should error.
998 self.executor_server.hold_jobs_in_build = True
999 A = self.fake_gerrit.addFakeChange('org/norole-project', 'master', 'A')
1000 self.fake_gerrit.addEvent(A.getPatchsetCreatedEvent(1))
1001 self.waitUntilSettled()
1002
1003 self.assertEqual(len(self.builds), 2)
1004 build = self.getBuildByName('implicit-role-fail')
1005 self._assertRolePath(build, 'playbook_0', None)
1006
1007 self.executor_server.hold_jobs_in_build = False
1008 self.executor_server.release()
1009 self.waitUntilSettled()
1010 # The retry_limit doesn't get recorded
1011 self.assertHistory([
1012 dict(name='implicit-role-fail', result='SUCCESS', changes='1,1'),
1013 ])
1014
1015 def test_roles(self):
1016 # Test implicit and explicit roles for a project which does
1017 # have roles. In both cases, we should end up with the role
1018 # in the path. In the explicit case, ensure we end up with
1019 # the name we specified.
1020 self.executor_server.hold_jobs_in_build = True
1021 A = self.fake_gerrit.addFakeChange('org/role-project', 'master', 'A')
1022 self.fake_gerrit.addEvent(A.getPatchsetCreatedEvent(1))
1023 self.waitUntilSettled()
1024
1025 self.assertEqual(len(self.builds), 2)
1026 build = self.getBuildByName('implicit-role-ok')
1027 self._assertRolePath(build, 'playbook_0', 'role_0')
1028
1029 build = self.getBuildByName('explicit-role-ok')
1030 self._assertRolePath(build, 'playbook_0', 'role_0')
1031
1032 self.executor_server.hold_jobs_in_build = False
1033 self.executor_server.release()
1034 self.waitUntilSettled()
1035 self.assertHistory([
1036 dict(name='implicit-role-ok', result='SUCCESS', changes='1,1'),
1037 dict(name='explicit-role-ok', result='SUCCESS', changes='1,1'),
1038 ], ordered=False)
1039
1040
James E. Blair6459db12017-06-29 14:57:20 -07001041class TestShadow(ZuulTestCase):
1042 tenant_config_file = 'config/shadow/main.yaml'
1043
1044 def test_shadow(self):
1045 # Test that a repo is allowed to shadow another's job definitions.
1046 A = self.fake_gerrit.addFakeChange('org/project', 'master', 'A')
1047 self.fake_gerrit.addEvent(A.getPatchsetCreatedEvent(1))
1048 self.waitUntilSettled()
1049 self.assertHistory([
1050 dict(name='test1', result='SUCCESS', changes='1,1'),
1051 dict(name='test2', result='SUCCESS', changes='1,1'),
James E. Blairadafa6c2017-07-12 08:50:56 -07001052 ], ordered=False)
James E. Blair196f61a2017-06-30 15:42:29 -07001053
1054
1055class TestDataReturn(AnsibleZuulTestCase):
1056 tenant_config_file = 'config/data-return/main.yaml'
1057
1058 def test_data_return(self):
1059 # This exercises a proposed change to a role being checked out
1060 # and used.
1061 A = self.fake_gerrit.addFakeChange('org/project', 'master', 'A')
1062 self.fake_gerrit.addEvent(A.getPatchsetCreatedEvent(1))
1063 self.waitUntilSettled()
1064 self.assertHistory([
1065 dict(name='data-return', result='SUCCESS', changes='1,1'),
James E. Blair88e79c02017-07-07 13:36:54 -07001066 dict(name='data-return-relative', result='SUCCESS', changes='1,1'),
1067 ], ordered=False)
1068 self.assertIn('- data-return http://example.com/test/log/url/',
1069 A.messages[-1])
1070 self.assertIn('- data-return-relative '
1071 'http://example.com/test/log/url/docs/index.html',
James E. Blair196f61a2017-06-30 15:42:29 -07001072 A.messages[-1])
Clint Byrumdc8a0902017-07-20 16:36:27 -07001073
1074
1075class TestDiskAccounting(AnsibleZuulTestCase):
1076 config_file = 'zuul-disk-accounting.conf'
1077 tenant_config_file = 'config/disk-accountant/main.yaml'
1078
1079 def test_disk_accountant_kills_job(self):
1080 A = self.fake_gerrit.addFakeChange('org/project', 'master', 'A')
1081 self.fake_gerrit.addEvent(A.getPatchsetCreatedEvent(1))
1082 self.waitUntilSettled()
1083 self.assertHistory([
1084 dict(name='dd-big-empty-file', result='ABORTED', changes='1,1')])
Tristan Cacqueray82f864b2017-08-01 05:54:42 +00001085
1086
1087class TestMaxNodesPerJob(AnsibleZuulTestCase):
1088 tenant_config_file = 'config/multi-tenant/main.yaml'
1089
1090 def test_max_nodes_reached(self):
1091 in_repo_conf = textwrap.dedent(
1092 """
1093 - job:
1094 name: test-job
1095 nodes:
1096 - name: node01
1097 label: fake
1098 - name: node02
1099 label: fake
1100 - name: node03
1101 label: fake
1102 - name: node04
1103 label: fake
1104 - name: node05
1105 label: fake
1106 - name: node06
1107 label: fake
1108 """)
1109 file_dict = {'.zuul.yaml': in_repo_conf}
1110 A = self.fake_gerrit.addFakeChange('org/project1', 'master', 'A',
1111 files=file_dict)
1112 self.fake_gerrit.addEvent(A.getPatchsetCreatedEvent(1))
1113 self.waitUntilSettled()
1114 self.assertIn('The job "test-job" exceeds tenant max-nodes-per-job 5.',
1115 A.messages[0], "A should fail because of nodes limit")
1116
1117 B = self.fake_gerrit.addFakeChange('org/project2', 'master', 'A',
1118 files=file_dict)
1119 self.fake_gerrit.addEvent(B.getPatchsetCreatedEvent(1))
1120 self.waitUntilSettled()
1121 self.assertNotIn("exceeds tenant max-nodes", B.messages[0],
1122 "B should not fail because of nodes limit")
James E. Blair2bab6e72017-08-07 09:52:45 -07001123
1124
1125class TestBaseJobs(ZuulTestCase):
1126 tenant_config_file = 'config/base-jobs/main.yaml'
1127
1128 def test_multiple_base_jobs(self):
1129 A = self.fake_gerrit.addFakeChange('org/project', 'master', 'A')
1130 self.fake_gerrit.addEvent(A.getPatchsetCreatedEvent(1))
1131 self.waitUntilSettled()
1132 self.assertHistory([
1133 dict(name='my-job', result='SUCCESS', changes='1,1'),
1134 dict(name='other-job', result='SUCCESS', changes='1,1'),
1135 ], ordered=False)
1136 self.assertEqual(self.getJobFromHistory('my-job').
1137 parameters['zuul']['jobtags'],
1138 ['mybase'])
1139 self.assertEqual(self.getJobFromHistory('other-job').
1140 parameters['zuul']['jobtags'],
1141 ['otherbase'])
1142
1143 def test_untrusted_base_job(self):
1144 """Test that a base job may not be defined in an untrusted repo"""
1145 in_repo_conf = textwrap.dedent(
1146 """
1147 - job:
1148 name: fail-base
1149 parent: null
1150 """)
1151
1152 file_dict = {'.zuul.yaml': in_repo_conf}
1153 A = self.fake_gerrit.addFakeChange('org/project', 'master', 'A',
1154 files=file_dict)
1155 self.fake_gerrit.addEvent(A.getPatchsetCreatedEvent(1))
1156 self.waitUntilSettled()
1157 self.assertEqual(A.reported, 1,
1158 "A should report failure")
1159 self.assertEqual(A.patchsets[0]['approvals'][0]['value'], "-1")
1160 self.assertIn('Base jobs must be defined in config projects',
1161 A.messages[0])
1162 self.assertHistory([])