This commit provides an environment option to change the behaviour so
that it's possible to declare any changes shoudl be considered a junit
failure.
This is useful when carrying out idempotent testing to ensure that
multiple runs are safe and any changes should be considered a test
failure.
In a CI test of an ansible role the practice would be to run the role
once without this to configure the test system, and tehn to run a second
time including this environment vairable so that the CI engine
processing the junit report recognise any changes to be a test fail.
... | ... |
@@ -115,6 +115,7 @@ Ansible Changes By Release |
115 | 115 |
* Update ipaddr Jinja filters to replace existing non RFC compliant ones. Added additional filters for easier use |
116 | 116 |
of handling IP addresses. (PR# 26566) |
117 | 117 |
* datetime filter updated to use default format of datetime.datetime (ISO8601) |
118 |
+* The junit plugin now has an option to report a junit test failure on changes for idempotent testing. |
|
118 | 119 |
|
119 | 120 |
#### New Callbacks: |
120 | 121 |
- full_skip |
... | ... |
@@ -58,6 +58,8 @@ class CallbackModule(CallbackBase): |
58 | 58 |
Default: ~/.ansible.log |
59 | 59 |
JUNIT_TASK_CLASS (optional): Configure the output to be one class per yaml file |
60 | 60 |
Default: False |
61 |
+ JUNIT_FAIL_ON_CHANGE (optional): Consider any tasks reporting "changed" as a junit test failure |
|
62 |
+ Default: False |
|
61 | 63 |
|
62 | 64 |
Requires: |
63 | 65 |
junit_xml |
... | ... |
@@ -74,6 +76,7 @@ class CallbackModule(CallbackBase): |
74 | 74 |
|
75 | 75 |
self._output_dir = os.getenv('JUNIT_OUTPUT_DIR', os.path.expanduser('~/.ansible.log')) |
76 | 76 |
self._task_class = os.getenv('JUNIT_TASK_CLASS', 'False').lower() |
77 |
+ self._fail_on_change = os.getenv('JUNIT_FAIL_ON_CHANGE', 'False').lower() |
|
77 | 78 |
self._playbook_path = None |
78 | 79 |
self._playbook_name = None |
79 | 80 |
self._play_name = None |
... | ... |
@@ -129,6 +132,9 @@ class CallbackModule(CallbackBase): |
129 | 129 |
|
130 | 130 |
task_data = self._task_data[task_uuid] |
131 | 131 |
|
132 |
+ if self._fail_on_change == 'true' and status == 'changed': |
|
133 |
+ status = 'failed' |
|
134 |
+ |
|
132 | 135 |
if status == 'failed' and 'EXPECTED FAILURE' in task_data.name: |
133 | 136 |
status = 'ok' |
134 | 137 |
|
... | ... |
@@ -224,7 +230,10 @@ class CallbackModule(CallbackBase): |
224 | 224 |
self._finish_task('failed', result) |
225 | 225 |
|
226 | 226 |
def v2_runner_on_ok(self, result): |
227 |
- self._finish_task('ok', result) |
|
227 |
+ if result._result.get('changed', False): |
|
228 |
+ self._finish_task('changed', result) |
|
229 |
+ else: |
|
230 |
+ self._finish_task('ok', result) |
|
228 | 231 |
|
229 | 232 |
def v2_runner_on_skipped(self, result): |
230 | 233 |
self._finish_task('skipped', result) |