mirror of
https://github.com/ansible/awx.git
synced 2026-01-22 15:08:03 -03:30
fix completeness
This commit is contained in:
parent
4cd4845617
commit
ec312358e2
@ -740,3 +740,37 @@ class TowerAPIModule(TowerModule):
|
||||
def wait_output(self, response):
|
||||
for k in ('id', 'status', 'elapsed', 'started', 'finished'):
|
||||
self.json_output[k] = response['json'].get(k)
|
||||
|
||||
def wait_on_workflow_node_url(self, url, object_name, object_type, timeout=30, interval=10, **kwargs):
|
||||
# Grab our start time to compare against for the timeout
|
||||
start = time.time()
|
||||
result = self.get_endpoint(url, **kwargs)
|
||||
|
||||
while result["json"]["count"] == 0:
|
||||
# If we are past our time out fail with a message
|
||||
if timeout and timeout < time.time() - start:
|
||||
# Account for Legacy messages
|
||||
self.json_output["msg"] = "Monitoring of {0} - {1} aborted due to timeout, {2}".format(object_type, object_name, url)
|
||||
self.wait_output(result)
|
||||
self.fail_json(**self.json_output)
|
||||
|
||||
# Put the process to sleep for our interval
|
||||
time.sleep(interval)
|
||||
result = self.get_endpoint(url, **kwargs)
|
||||
|
||||
if object_type == "Workflow Approval":
|
||||
# Approval jobs have no elapsed time so return
|
||||
return result["json"]["results"][0]
|
||||
else:
|
||||
# Removed time so far from timeout.
|
||||
revised_timeout = timeout - (time.time() - start)
|
||||
# Now that Job has been found, wait for it to finish
|
||||
result = self.wait_on_url(
|
||||
url=result["json"]["results"][0]["related"]["job"],
|
||||
object_name=object_name,
|
||||
object_type=object_type,
|
||||
timeout=revised_timeout,
|
||||
interval=interval,
|
||||
)
|
||||
self.json_output["job_data"] = result["json"]
|
||||
return result
|
||||
|
||||
125
awx_collection/plugins/modules/tower_workflow_approval.py
Normal file
125
awx_collection/plugins/modules/tower_workflow_approval.py
Normal file
@ -0,0 +1,125 @@
|
||||
#!/usr/bin/python
|
||||
# coding: utf-8 -*-
|
||||
|
||||
# (c) 2021, Sean Sullivan
|
||||
# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt)
|
||||
|
||||
from __future__ import absolute_import, division, print_function
|
||||
|
||||
__metaclass__ = type
|
||||
|
||||
|
||||
ANSIBLE_METADATA = {
|
||||
"metadata_version": "1.1",
|
||||
"status": ["preview"],
|
||||
"supported_by": "community",
|
||||
}
|
||||
|
||||
|
||||
DOCUMENTATION = """
|
||||
---
|
||||
module: tower_workflow_approval
|
||||
author: "Sean Sullivan (@sean-m-sullivan)"
|
||||
short_description: Approve an approval node in a workflow job.
|
||||
description:
|
||||
- Approve an approval node in a workflow job. See
|
||||
U(https://www.ansible.com/tower) for an overview.
|
||||
options:
|
||||
workflow_job_id:
|
||||
description:
|
||||
- ID of the workflow job to monitor for approval.
|
||||
required: True
|
||||
type: int
|
||||
name:
|
||||
description:
|
||||
- Name of the Approval node to approve or deny.
|
||||
required: True
|
||||
type: str
|
||||
action:
|
||||
description:
|
||||
- Type of action to take.
|
||||
choices: ["approve", "deny"]
|
||||
default: "approve"
|
||||
type: str
|
||||
interval:
|
||||
description:
|
||||
- The interval in sections, to request an update from Tower.
|
||||
required: False
|
||||
default: 1
|
||||
type: float
|
||||
timeout:
|
||||
description:
|
||||
- Maximum time in seconds to wait for a workflow job to to reach approval node.
|
||||
default: 10
|
||||
type: int
|
||||
extends_documentation_fragment: awx.awx.auth
|
||||
"""
|
||||
|
||||
|
||||
EXAMPLES = """
|
||||
- name: Launch a workflow with a timeout of 10 seconds
|
||||
tower_workflow_launch:
|
||||
workflow_template: "Test Workflow"
|
||||
wait: False
|
||||
register: workflow
|
||||
|
||||
- name: Wait for approval node to activate and approve
|
||||
tower_workflow_approval:
|
||||
workflow_job_id: "{{ workflow.id }}"
|
||||
name: Approve Me
|
||||
interval: 10
|
||||
timeout: 20
|
||||
action: deny
|
||||
"""
|
||||
|
||||
RETURN = """
|
||||
|
||||
"""
|
||||
|
||||
|
||||
from ..module_utils.tower_api import TowerAPIModule
|
||||
|
||||
|
||||
def main():
|
||||
# Any additional arguments that are not fields of the item can be added here
|
||||
argument_spec = dict(
|
||||
workflow_job_id=dict(type="int", required=True),
|
||||
name=dict(required=True),
|
||||
action=dict(choices=["approve", "deny"], default="approve"),
|
||||
timeout=dict(type="int", default=10),
|
||||
interval=dict(type="float", default=1),
|
||||
)
|
||||
|
||||
# Create a module for ourselves
|
||||
module = TowerAPIModule(argument_spec=argument_spec)
|
||||
|
||||
# Extract our parameters
|
||||
workflow_job_id = module.params.get("workflow_job_id")
|
||||
name = module.params.get("name")
|
||||
action = module.params.get("action")
|
||||
timeout = module.params.get("timeout")
|
||||
interval = module.params.get("interval")
|
||||
|
||||
# Attempt to look up workflow job based on the provided id
|
||||
approval_job = module.wait_on_workflow_node_url(
|
||||
url="workflow_jobs/{0}/workflow_nodes/".format(workflow_job_id),
|
||||
object_name=name,
|
||||
object_type="Workflow Approval",
|
||||
timeout=timeout,
|
||||
interval=interval,
|
||||
**{
|
||||
"data": {
|
||||
"job__name": name,
|
||||
}
|
||||
}
|
||||
)
|
||||
response = module.post_endpoint("{0}{1}".format(approval_job["related"]["job"], action))
|
||||
if response["status_code"] == 204:
|
||||
module.json_output["changed"] = True
|
||||
|
||||
# Attempt to look up jobs based on the status
|
||||
module.exit_json(**module.json_output)
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
main()
|
||||
115
awx_collection/plugins/modules/tower_workflow_node_wait.py
Normal file
115
awx_collection/plugins/modules/tower_workflow_node_wait.py
Normal file
@ -0,0 +1,115 @@
|
||||
#!/usr/bin/python
|
||||
# coding: utf-8 -*-
|
||||
|
||||
# (c) 2021, Sean Sullivan
|
||||
# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt)
|
||||
|
||||
from __future__ import absolute_import, division, print_function
|
||||
|
||||
__metaclass__ = type
|
||||
|
||||
|
||||
ANSIBLE_METADATA = {
|
||||
"metadata_version": "1.1",
|
||||
"status": ["preview"],
|
||||
"supported_by": "community",
|
||||
}
|
||||
|
||||
|
||||
DOCUMENTATION = """
|
||||
---
|
||||
module: tower_workflow_node_wait
|
||||
author: "Sean Sullivan (@sean-m-sullivan)"
|
||||
short_description: Approve an approval node in a workflow job.
|
||||
description:
|
||||
- Approve an approval node in a workflow job. See
|
||||
U(https://www.ansible.com/tower) for an overview.
|
||||
options:
|
||||
workflow_job_id:
|
||||
description:
|
||||
- ID of the workflow job to monitor for node.
|
||||
required: True
|
||||
type: int
|
||||
name:
|
||||
description:
|
||||
- Name of the workflow node to wait on.
|
||||
required: True
|
||||
type: str
|
||||
interval:
|
||||
description:
|
||||
- The interval in sections, to request an update from Tower.
|
||||
required: False
|
||||
default: 1
|
||||
type: float
|
||||
timeout:
|
||||
description:
|
||||
- Maximum time in seconds to wait for a workflow job to to reach approval node.
|
||||
default: 10
|
||||
type: int
|
||||
extends_documentation_fragment: awx.awx.auth
|
||||
"""
|
||||
|
||||
|
||||
EXAMPLES = """
|
||||
- name: Launch a workflow with a timeout of 10 seconds
|
||||
tower_workflow_launch:
|
||||
workflow_template: "Test Workflow"
|
||||
wait: False
|
||||
register: workflow
|
||||
|
||||
- name: Wait for a workflow node to finish
|
||||
tower_workflow_node_wait:
|
||||
workflow_job_id: "{{ workflow.id }}"
|
||||
name: Approval Data Step
|
||||
timeout: 120
|
||||
"""
|
||||
|
||||
RETURN = """
|
||||
|
||||
"""
|
||||
|
||||
|
||||
from ..module_utils.tower_api import TowerAPIModule
|
||||
import time
|
||||
|
||||
|
||||
def main():
|
||||
# Any additional arguments that are not fields of the item can be added here
|
||||
argument_spec = dict(
|
||||
workflow_job_id=dict(type="int", required=True),
|
||||
name=dict(required=True),
|
||||
timeout=dict(type="int", default=10),
|
||||
interval=dict(type="float", default=1),
|
||||
)
|
||||
|
||||
# Create a module for ourselves
|
||||
module = TowerAPIModule(argument_spec=argument_spec)
|
||||
|
||||
# Extract our parameters
|
||||
workflow_job_id = module.params.get("workflow_job_id")
|
||||
name = module.params.get("name")
|
||||
timeout = module.params.get("timeout")
|
||||
interval = module.params.get("interval")
|
||||
|
||||
node_url = "workflow_jobs/{0}/workflow_nodes/?job__name={1}".format(workflow_job_id, name)
|
||||
# Attempt to look up workflow job node based on the provided id
|
||||
|
||||
result = module.wait_on_workflow_node_url(
|
||||
url="workflow_jobs/{0}/workflow_nodes/".format(workflow_job_id),
|
||||
object_name=name,
|
||||
object_type="Workflow Node",
|
||||
timeout=timeout,
|
||||
interval=interval,
|
||||
**{
|
||||
"data": {
|
||||
"job__name": name,
|
||||
}
|
||||
}
|
||||
)
|
||||
|
||||
# Attempt to look up jobs based on the status
|
||||
module.exit_json(**module.json_output)
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
main()
|
||||
@ -36,6 +36,7 @@ no_endpoint_for_module = [
|
||||
'tower_receive',
|
||||
'tower_send',
|
||||
'tower_workflow_launch',
|
||||
'tower_workflow_node_wait',
|
||||
'tower_job_cancel',
|
||||
'tower_workflow_template',
|
||||
'tower_ad_hoc_command_wait',
|
||||
@ -64,16 +65,17 @@ no_api_parameter_ok = {
|
||||
'tower_ad_hoc_command': ['interval', 'timeout', 'wait'],
|
||||
# tower_group parameters to perserve hosts and children.
|
||||
'tower_group': ['preserve_existing_children', 'preserve_existing_hosts'],
|
||||
# tower_workflow_approval parameters that do not apply when approving an approval node.
|
||||
'tower_workflow_approval': ['action', 'interval', 'timeout', 'workflow_job_id'],
|
||||
}
|
||||
|
||||
# When this tool was created we were not feature complete. Adding something in here indicates a module
|
||||
# that needs to be developed. If the module is found on the file system it will auto-detect that the
|
||||
# work is being done and will bypass this check. At some point this module should be removed from this list.
|
||||
needs_development = [
|
||||
'tower_workflow_approval',
|
||||
]
|
||||
needs_development = ['tower_inventory_script']
|
||||
needs_param_development = {
|
||||
'tower_host': ['instance_id'],
|
||||
'tower_workflow_approval': ['description', 'execution_environment'],
|
||||
}
|
||||
# -----------------------------------------------------------------------------------------------------------
|
||||
|
||||
|
||||
@ -7,146 +7,237 @@
|
||||
- name: Generate names
|
||||
set_fact:
|
||||
wfjt_name1: "AWX-Collection-tests-tower_workflow_launch--wfjt1-{{ test_id }}"
|
||||
wfjt_name2: "AWX-Collection-tests-tower_workflow_launch--wfjt1-{{ test_id }}-2"
|
||||
approval_node_name: "AWX-Collection-tests-tower_workflow_launch_approval_node-{{ test_id }}"
|
||||
|
||||
- name: Create our workflow
|
||||
tower_workflow_job_template:
|
||||
name: "{{ wfjt_name1 }}"
|
||||
state: present
|
||||
- block:
|
||||
|
||||
- name: Add a node
|
||||
tower_workflow_job_template_node:
|
||||
workflow_job_template: "{{ wfjt_name1 }}"
|
||||
unified_job_template: "Demo Job Template"
|
||||
identifier: leaf
|
||||
register: new_node
|
||||
- name: Create our workflow
|
||||
tower_workflow_job_template:
|
||||
name: "{{ wfjt_name1 }}"
|
||||
state: present
|
||||
|
||||
- name: Connect to Tower server but request an invalid workflow
|
||||
tower_workflow_launch:
|
||||
workflow_template: "Does Not Exist"
|
||||
ignore_errors: true
|
||||
register: result
|
||||
- name: Add a node
|
||||
tower_workflow_job_template_node:
|
||||
workflow_job_template: "{{ wfjt_name1 }}"
|
||||
unified_job_template: "Demo Job Template"
|
||||
identifier: leaf
|
||||
register: new_node
|
||||
|
||||
- assert:
|
||||
that:
|
||||
- result is failed
|
||||
- "'Unable to find workflow job template' in result.msg"
|
||||
- name: Connect to Tower server but request an invalid workflow
|
||||
tower_workflow_launch:
|
||||
workflow_template: "Does Not Exist"
|
||||
ignore_errors: true
|
||||
register: result
|
||||
|
||||
- name: Run the workflow without waiting (this should just give us back a job ID)
|
||||
tower_workflow_launch:
|
||||
workflow_template: "{{ wfjt_name1 }}"
|
||||
wait: false
|
||||
ignore_errors: true
|
||||
register: result
|
||||
- assert:
|
||||
that:
|
||||
- result is failed
|
||||
- "'Unable to find workflow job template' in result.msg"
|
||||
|
||||
- assert:
|
||||
that:
|
||||
- result is not failed
|
||||
- "'id' in result['job_info']"
|
||||
- name: Run the workflow without waiting (this should just give us back a job ID)
|
||||
tower_workflow_launch:
|
||||
workflow_template: "{{ wfjt_name1 }}"
|
||||
wait: false
|
||||
ignore_errors: true
|
||||
register: result
|
||||
|
||||
- name: Kick off a workflow and wait for it, but only for a second
|
||||
tower_workflow_launch:
|
||||
workflow_template: "{{ wfjt_name1 }}"
|
||||
timeout: 1
|
||||
ignore_errors: true
|
||||
register: result
|
||||
- assert:
|
||||
that:
|
||||
- result is not failed
|
||||
- "'id' in result['job_info']"
|
||||
|
||||
- assert:
|
||||
that:
|
||||
- result is failed
|
||||
- "'Monitoring of Workflow Job - {{ wfjt_name1 }} aborted due to timeout' in result.msg"
|
||||
- name: Kick off a workflow and wait for it, but only for a second
|
||||
tower_workflow_launch:
|
||||
workflow_template: "{{ wfjt_name1 }}"
|
||||
timeout: 1
|
||||
ignore_errors: true
|
||||
register: result
|
||||
|
||||
- name: Kick off a workflow and wait for it
|
||||
tower_workflow_launch:
|
||||
workflow_template: "{{ wfjt_name1 }}"
|
||||
ignore_errors: true
|
||||
register: result
|
||||
- assert:
|
||||
that:
|
||||
- result is failed
|
||||
- "'Monitoring of Workflow Job - {{ wfjt_name1 }} aborted due to timeout' in result.msg"
|
||||
|
||||
- assert:
|
||||
that:
|
||||
- result is not failed
|
||||
- "'id' in result['job_info']"
|
||||
- name: Kick off a workflow and wait for it
|
||||
tower_workflow_launch:
|
||||
workflow_template: "{{ wfjt_name1 }}"
|
||||
ignore_errors: true
|
||||
register: result
|
||||
|
||||
- name: Kick off a workflow with extra_vars but not enabled
|
||||
tower_workflow_launch:
|
||||
workflow_template: "{{ wfjt_name1 }}"
|
||||
extra_vars:
|
||||
var1: My First Variable
|
||||
var2: My Second Variable
|
||||
ignore_errors: true
|
||||
register: result
|
||||
- assert:
|
||||
that:
|
||||
- result is not failed
|
||||
- "'id' in result['job_info']"
|
||||
|
||||
- assert:
|
||||
that:
|
||||
- result is failed
|
||||
- "'The field extra_vars was specified but the workflow job template does not allow for it to be overridden' in result.errors"
|
||||
- name: Kick off a workflow with extra_vars but not enabled
|
||||
tower_workflow_launch:
|
||||
workflow_template: "{{ wfjt_name1 }}"
|
||||
extra_vars:
|
||||
var1: My First Variable
|
||||
var2: My Second Variable
|
||||
ignore_errors: true
|
||||
register: result
|
||||
|
||||
- name: Prompt the workflow's with survey
|
||||
tower_workflow_job_template:
|
||||
name: "{{ wfjt_name1 }}"
|
||||
state: present
|
||||
survey_enabled: true
|
||||
ask_variables_on_launch: false
|
||||
survey:
|
||||
name: ''
|
||||
description: ''
|
||||
spec:
|
||||
- question_name: Basic Name
|
||||
question_description: Name
|
||||
required: true
|
||||
type: text
|
||||
variable: basic_name
|
||||
min: 0
|
||||
max: 1024
|
||||
default: ''
|
||||
choices: ''
|
||||
new_question: true
|
||||
- question_name: Choose yes or no?
|
||||
question_description: Choosing yes or no.
|
||||
required: false
|
||||
type: multiplechoice
|
||||
variable: option_true_false
|
||||
min:
|
||||
max:
|
||||
default: 'yes'
|
||||
choices: |-
|
||||
yes
|
||||
no
|
||||
new_question: true
|
||||
- assert:
|
||||
that:
|
||||
- result is failed
|
||||
- "'The field extra_vars was specified but the workflow job template does not allow for it to be overridden' in result.errors"
|
||||
|
||||
- name: Kick off a workflow with survey
|
||||
tower_workflow_launch:
|
||||
workflow_template: "{{ wfjt_name1 }}"
|
||||
extra_vars:
|
||||
basic_name: My First Variable
|
||||
option_true_false: 'no'
|
||||
ignore_errors: true
|
||||
register: result
|
||||
- name: Prompt the workflow's with survey
|
||||
tower_workflow_job_template:
|
||||
name: "{{ wfjt_name1 }}"
|
||||
state: present
|
||||
survey_enabled: true
|
||||
ask_variables_on_launch: false
|
||||
survey:
|
||||
name: ''
|
||||
description: ''
|
||||
spec:
|
||||
- question_name: Basic Name
|
||||
question_description: Name
|
||||
required: true
|
||||
type: text
|
||||
variable: basic_name
|
||||
min: 0
|
||||
max: 1024
|
||||
default: ''
|
||||
choices: ''
|
||||
new_question: true
|
||||
- question_name: Choose yes or no?
|
||||
question_description: Choosing yes or no.
|
||||
required: false
|
||||
type: multiplechoice
|
||||
variable: option_true_false
|
||||
min:
|
||||
max:
|
||||
default: 'yes'
|
||||
choices: |-
|
||||
yes
|
||||
no
|
||||
new_question: true
|
||||
|
||||
- assert:
|
||||
that:
|
||||
- result is not failed
|
||||
- name: Kick off a workflow with survey
|
||||
tower_workflow_launch:
|
||||
workflow_template: "{{ wfjt_name1 }}"
|
||||
extra_vars:
|
||||
basic_name: My First Variable
|
||||
option_true_false: 'no'
|
||||
ignore_errors: true
|
||||
register: result
|
||||
|
||||
- name: Prompt the workflow's extra_vars on launch
|
||||
tower_workflow_job_template:
|
||||
name: "{{ wfjt_name1 }}"
|
||||
state: present
|
||||
ask_variables_on_launch: true
|
||||
- assert:
|
||||
that:
|
||||
- result is not failed
|
||||
|
||||
- name: Kick off a workflow with extra_vars
|
||||
tower_workflow_launch:
|
||||
workflow_template: "{{ wfjt_name1 }}"
|
||||
extra_vars:
|
||||
basic_name: My First Variable
|
||||
var1: My First Variable
|
||||
var2: My Second Variable
|
||||
ignore_errors: true
|
||||
register: result
|
||||
- name: Prompt the workflow's extra_vars on launch
|
||||
tower_workflow_job_template:
|
||||
name: "{{ wfjt_name1 }}"
|
||||
state: present
|
||||
ask_variables_on_launch: true
|
||||
|
||||
- assert:
|
||||
that:
|
||||
- result is not failed
|
||||
- name: Kick off a workflow with extra_vars
|
||||
tower_workflow_launch:
|
||||
workflow_template: "{{ wfjt_name1 }}"
|
||||
extra_vars:
|
||||
basic_name: My First Variable
|
||||
var1: My First Variable
|
||||
var2: My Second Variable
|
||||
ignore_errors: true
|
||||
register: result
|
||||
|
||||
- name: Clean up test workflow
|
||||
tower_workflow_job_template:
|
||||
name: "{{ wfjt_name1 }}"
|
||||
state: absent
|
||||
- assert:
|
||||
that:
|
||||
- result is not failed
|
||||
|
||||
- name: Test waiting for an approval node that doesn't exit on the last workflow for failure.
|
||||
tower_workflow_approval:
|
||||
workflow_job_id: "{{ result.id }}"
|
||||
name: Test workflow approval
|
||||
interval: 1
|
||||
timeout: 2
|
||||
action: deny
|
||||
register: result
|
||||
ignore_errors: true
|
||||
|
||||
- assert:
|
||||
that:
|
||||
- result is failed
|
||||
- "'Monitoring of Workflow Approval - Test workflow approval aborted due to timeout' in result.msg"
|
||||
|
||||
- name: Create new Workflow
|
||||
tower_workflow_job_template:
|
||||
name: "{{ wfjt_name2 }}"
|
||||
state: present
|
||||
|
||||
- name: Add a job node
|
||||
tower_workflow_job_template_node:
|
||||
workflow_job_template: "{{ wfjt_name2 }}"
|
||||
unified_job_template: "Demo Job Template"
|
||||
identifier: leaf
|
||||
|
||||
# Test tower_workflow_approval and tower_workflow_node_wait
|
||||
- name: Create approval node
|
||||
tower_workflow_job_template_node:
|
||||
identifier: approval_test
|
||||
approval_node:
|
||||
name: "{{ approval_node_name }}"
|
||||
timeout: 900
|
||||
workflow: "{{ wfjt_name2 }}"
|
||||
|
||||
- name: Create link for approval node
|
||||
tower_workflow_job_template_node:
|
||||
identifier: approval_test
|
||||
workflow: "{{ wfjt_name2 }}"
|
||||
always_nodes:
|
||||
- leaf
|
||||
|
||||
- name: Run the workflow without waiting This should pause waiting for approval
|
||||
tower_workflow_launch:
|
||||
workflow_template: "{{ wfjt_name2 }}"
|
||||
wait: false
|
||||
ignore_errors: true
|
||||
register: wfjt_info
|
||||
|
||||
- name: Wait for Job node wait to fail as it is waiting on approval
|
||||
awx.awx.tower_workflow_node_wait:
|
||||
workflow_job_id: "{{ wfjt_info.id }}"
|
||||
name: Demo Job Template
|
||||
interval: 1
|
||||
timeout: 5
|
||||
register: result
|
||||
ignore_errors: true
|
||||
|
||||
- assert:
|
||||
that:
|
||||
- result is failed
|
||||
- "'Monitoring of Workflow Node - Demo Job Template aborted due to timeout' in result.msg"
|
||||
|
||||
- name: Wait for approval node to activate and approve
|
||||
awx.awx.tower_workflow_approval:
|
||||
workflow_job_id: "{{ wfjt_info.id }}"
|
||||
name: "{{ approval_node_name }}"
|
||||
interval: 1
|
||||
timeout: 10
|
||||
action: deny
|
||||
register: result
|
||||
|
||||
- assert:
|
||||
that:
|
||||
- result is not failed
|
||||
- result is changed
|
||||
|
||||
- name: Wait for workflow job to finish max 120s
|
||||
tower_job_wait:
|
||||
job_id: "{{ wfjt_info.id }}"
|
||||
timeout: 120
|
||||
job_type: "workflow_jobs"
|
||||
|
||||
always:
|
||||
- name: Clean up test workflow
|
||||
tower_workflow_job_template:
|
||||
name: "{{ item }}"
|
||||
state: absent
|
||||
with_items:
|
||||
- "{{ wfjt_name1 }}"
|
||||
- "{{ wfjt_name2 }}"
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user