From bb8a3e18b815f380e768aa34849a9cb31e7c78fa Mon Sep 17 00:00:00 2001 From: "Brad P. Crochet" Date: Thu, 12 Oct 2017 10:37:40 -0400 Subject: [PATCH] Add UpdateNetworks workflow Change-Id: I3faddc2af372ae34bed127efb89e41c667fecfe6 Implements: blueprint update-networks-action Depends-On: Icfdebe0728051607c0519ddb00ea7e54630dc06c --- setup.cfg | 1 + tripleo_common/actions/plan.py | 23 +++ tripleo_common/tests/actions/test_plan.py | 46 +++++ workbooks/networks.yaml | 208 ++++++++++++++++++++++ workbooks/plan_management.yaml | 64 +++++-- 5 files changed, 332 insertions(+), 10 deletions(-) create mode 100644 workbooks/networks.yaml diff --git a/setup.cfg b/setup.cfg index b2a7da9c5..41f576e69 100644 --- a/setup.cfg +++ b/setup.cfg @@ -111,6 +111,7 @@ mistral.actions = tripleo.plan.list = tripleo_common.actions.plan:ListPlansAction tripleo.plan.export = tripleo_common.actions.plan:ExportPlanAction tripleo.plan.update_from_dir = tripleo_common.actions.plan:UpdatePlanFromDirAction + tripleo.plan.update_networks = tripleo_common.actions.plan:UpdateNetworksAction tripleo.plan.update_plan_environment = tripleo_common.actions.plan:UpdatePlanEnvironmentAction tripleo.logging_to_swift.format_messages = tripleo_common.actions.logging_to_swift:FormatMessagesAction tripleo.logging_to_swift.publish_ui_log_to_swift = tripleo_common.actions.logging_to_swift:PublishUILogToSwiftAction diff --git a/tripleo_common/actions/plan.py b/tripleo_common/actions/plan.py index 1e9694650..458d490d4 100644 --- a/tripleo_common/actions/plan.py +++ b/tripleo_common/actions/plan.py @@ -323,3 +323,26 @@ class UpdatePlanEnvironmentAction(base.TripleOAction): except Exception as err: msg = "Error while updating plan: %s" % err return actions.Result(error=msg) + + +class UpdateNetworksAction(base.TripleOAction): + def __init__(self, networks, current_networks, replace_all=False): + super(UpdateNetworksAction, self).__init__() + self.networks = networks + self.current_networks = current_networks + self.replace_all = replace_all + + def run(self, context): + network_data_to_save = self.networks or [] + + # if replace_all flag is true, discard current networks and save input + # if replace_all flag is false, merge input into current networks + if not self.replace_all: + # merge the networks_data and the network_input into networks + # to be saved + network_data_to_save = [net for net in { + x['name']: x for x in + self.current_networks + self.networks + }.values()] + + return actions.Result(data={'network_data': network_data_to_save}) diff --git a/tripleo_common/tests/actions/test_plan.py b/tripleo_common/tests/actions/test_plan.py index 2a04e44f9..66868b52f 100644 --- a/tripleo_common/tests/actions/test_plan.py +++ b/tripleo_common/tests/actions/test_plan.py @@ -400,3 +400,49 @@ class ExportPlanActionTest(base.TestCase): error = "Error while creating a tarball" self.assertIn(error, result.error) + + +class UpdateNetworksActionTest(base.TestCase): + + def setUp(self): + super(UpdateNetworksActionTest, self).setUp() + self.current_networks = [ + { + 'name': 'FirstCurrentNetwork' + } + ] + self.ctx = mock.MagicMock() + + def test_run_success(self): + networks = [ + { + 'name': 'MyFirstNetwork' + } + ] + + action = plan.UpdateNetworksAction(networks, self.current_networks, + replace_all=False) + result = action.run(self.ctx) + + expected = [ + {'name': 'FirstCurrentNetwork'}, + {'name': 'MyFirstNetwork'} + ] + self.assertEqual(expected, + sorted(result.data['network_data'], + key=lambda k: k['name'])) + + def test_run_success_replace(self): + networks = [ + { + 'name': 'MyReplacementNetwork' + } + ] + + action = plan.UpdateNetworksAction(networks, self.current_networks, + replace_all=True) + result = action.run(self.ctx) + expected = [ + {'name': 'MyReplacementNetwork'} + ] + self.assertEqual({"network_data": expected}, result.data) diff --git a/workbooks/networks.yaml b/workbooks/networks.yaml new file mode 100644 index 000000000..f039a1b94 --- /dev/null +++ b/workbooks/networks.yaml @@ -0,0 +1,208 @@ +--- +version: '2.0' +name: tripleo.networks.v1 +description: TripleO Overcloud Networks Workflows v1 + +workflows: + + validate_networks_input: + description: > + Validate that required fields are present. + + input: + - networks + - queue_name: tripleo + + output: + result: <% task(validate_network_names).result %> + + tags: + - tripleo-common-managed + + tasks: + validate_network_names: + publish: + network_name_present: <% $.networks.all($.containsKey('name')) %> + on-success: + - set_status_success: <% $.network_name_present = true %> + - set_status_error: <% $.network_name_present = false %> + publish-on-error: + status: FAILED + message: <% task().result %> + on-error: notify_zaqar + + set_status_success: + on-success: notify_zaqar + publish: + status: SUCCESS + message: <% task(validate_network_names).result %> + + set_status_error: + on-success: notify_zaqar + publish: + status: FAILED + message: "One or more entries did not contain the required field 'name'" + + notify_zaqar: + action: zaqar.queue_post + input: + queue_name: <% $.queue_name %> + messages: + body: + type: tripleo.networks.v1.validate_networks_input + payload: + status: <% $.status %> + message: <% $.get('message', '') %> + execution: <% execution() %> + on-success: + - fail: <% $.get('status') = "FAILED" %> + + update_networks: + description: > + Takes data in networks parameter in json format, validates its contents, + and persists them in network_data.yaml. After successful update, + templates are regenerated. + + input: + - container: overcloud + - networks + - network_data_file: 'network_data.yaml' + - queue_name: tripleo + + output: + network_data: <% $.network_data %> + + tags: + - tripleo-common-managed + + tasks: + validate_input: + description: > + validate the format of input (input includes required fields for + each network) + workflow: validate_networks_input + input: + networks: <% $.networks %> + on-success: validate_network_files + publish-on-error: + status: FAILED + message: <% task().result %> + on-error: notify_zaqar + + validate_network_files: + description: > + validate that Network names exist in Swift container + workflow: tripleo.plan_management.v1.validate_network_files + input: + container: <% $.container %> + network_data: <% $.networks %> + queue_name: <% $.queue_name %> + publish: + network_data: <% task().network_data %> + on-success: get_available_networks + publish-on-error: + status: FAILED + message: <% task().result %> + on-error: notify_zaqar + + get_available_networks: + workflow: tripleo.plan_management.v1.list_available_networks + input: + container: <% $.container %> + queue_name: <% $.queue_name %> + publish: + available_networks: <% task().result.available_networks %> + on-success: get_current_networks + publish-on-error: + status: FAILED + message: <% task().result %> + on-error: notify_zaqar + + get_current_networks: + workflow: tripleo.plan_management.v1.get_network_data + input: + container: <% $.container %> + network_data_file: <% $.network_data_file %> + queue_name: <% $.queue_name %> + publish: + current_networks: <% task().result.network_data %> + on-success: update_network_data + publish-on-error: + status: FAILED + message: <% task().result %> + on-error: notify_zaqar + + update_network_data: + description: > + Combine (or replace) the network data + action: tripleo.plan.update_networks + input: + networks: <% $.available_networks %> + current_networks: <% $.current_networks %> + remove_all: false + publish: + new_network_data: <% task().result.network_data %> + on-success: update_network_data_in_swift + publish-on-error: + status: FAILED + message: <% task().result %> + on-error: notify_zaqar + + update_network_data_in_swift: + description: > + update network_data.yaml object in Swift with data from workflow input + action: swift.put_object + input: + container: <% $.container %> + obj: <% $.network_data_file %> + contents: <% yaml_dump($.new_network_data) %> + on-success: regenerate_templates + publish-on-error: + status: FAILED + message: <% task().result %> + on-error: notify_zaqar + + regenerate_templates: + action: tripleo.templates.process container=<% $.container %> + on-success: get_networks + publish-on-error: + status: FAILED + message: <% task().result %> + on-error: notify_zaqar + + get_networks: + description: > + run GetNetworksAction to get updated contents of network_data.yaml and + provide it as output + workflow: tripleo.plan_management.v1.get_network_data + input: + container: <% $.container %> + network_data_file: <% $.network_data_file %> + queue_name: <% $.queue_name %> + publish: + network_data: <% task().network_data %> + on-success: set_status_success + publish-on-error: + status: FAILED + message: <% task().result %> + on-error: notify_zaqar + + set_status_success: + on-success: notify_zaqar + publish: + status: SUCCESS + message: <% task(get_networks).result %> + + notify_zaqar: + action: zaqar.queue_post + input: + queue_name: <% $.queue_name %> + messages: + body: + type: tripleo.networks.v1.update_networks + payload: + status: <% $.status %> + message: <% $.get('message', '') %> + execution: <% execution() %> + on-success: + - fail: <% $.get('status') = "FAILED" %> diff --git a/workbooks/plan_management.yaml b/workbooks/plan_management.yaml index c8165bb94..fa53fc3ac 100644 --- a/workbooks/plan_management.yaml +++ b/workbooks/plan_management.yaml @@ -808,6 +808,55 @@ workflows: on-success: - fail: <% $.get('status') = "FAILED" %> + validate_network_files: + description: Validate network files exist + input: + - container: overcloud + - network_data + - queue_name: tripleo + + output: + network_data: <% $.network_data %> + + tags: + - tripleo-common-managed + + tasks: + get_network_names: + publish: + network_names_lower: <% $.network_data.where($.containsKey('name_lower')).name_lower %> + network_names: <% $.network_data.where(not $.containsKey('name_lower')).name %> + on-success: validate_networks + + validate_networks: + with-items: network in <% $.network_names_lower.concat($.network_names) %> + action: swift.head_object + input: + container: <% $.container %> + obj: network/<% $.network.toLower() %>.yaml + publish: + status: SUCCESS + message: <% task().result %> + on-success: notify_zaqar + publish-on-error: + status: FAILED + message: <% task().result %> + + notify_zaqar: + action: zaqar.queue_post + retry: count=5 delay=1 + input: + queue_name: <% $.queue_name %> + messages: + body: + type: tripleo.plan_management.v1.validate_network_files + payload: + status: <% $.status %> + message: <% $.message %> + execution: <% execution() %> + on-success: + - fail: <% $.get('status') = "FAILED" %> + validate_networks: description: Validate network files were generated properly and exist input: @@ -830,25 +879,19 @@ workflows: queue_name: <% $.queue_name %> publish: network_data: <% task().result.network_data %> - on-success: get_network_names + on-success: validate_networks publish-on-error: status: FAILED message: <% task().result %> on-error: notify_zaqar - get_network_names: - publish: - network_names_lower: <% $.network_data.where($.containsKey('name_lower')).name_lower %> - network_names: <% $.network_data.where(not $.containsKey('name_lower')).name %> - on-success: validate_networks - validate_networks: - with-items: network in <% $.network_names_lower.concat($.network_names) %> - action: swift.head_object + workflow: validate_network_files input: container: <% $.container %> - obj: network/<% $.network.toLower() %>.yaml + network_data: <% $.network_data %> + queue_name: <% $.queue_name %> publish: status: SUCCESS message: <% task().result %> @@ -856,6 +899,7 @@ workflows: publish-on-error: status: FAILED message: <% task().result %> + on-error: notify_zaqar notify_zaqar: action: zaqar.queue_post