From d65a91ea7ee4f7d3cc9924d0ea99f33da2be6068 Mon Sep 17 00:00:00 2001 From: Kevin Breit Date: Fri, 22 Feb 2019 18:39:01 -0600 Subject: [PATCH] meraki_config_template - Fix actions when specifying net_id (#51586) * Allow configuration templates when using net_id...for reals - Didn't work before, I had bad code. I'm sorry. - Cleaned up code and simplified functions - Added integration tests to test for net_id actions * Add changelog * Add module name to changelog * Fix indentation --- ...raki_configuration_template_net_id_fix.yml | 3 + .../network/meraki/meraki_config_template.py | 88 ++++++++--------- .../meraki_config_template/tasks/main.yml | 96 ++++++++++++++----- 3 files changed, 116 insertions(+), 71 deletions(-) create mode 100644 changelogs/fragments/meraki_configuration_template_net_id_fix.yml diff --git a/changelogs/fragments/meraki_configuration_template_net_id_fix.yml b/changelogs/fragments/meraki_configuration_template_net_id_fix.yml new file mode 100644 index 00000000000..8fb7f991c80 --- /dev/null +++ b/changelogs/fragments/meraki_configuration_template_net_id_fix.yml @@ -0,0 +1,3 @@ +bugfixes: + - meraki_config_template - Fix conditions which prevented code from executing when specifying net_id + \ No newline at end of file diff --git a/lib/ansible/modules/network/meraki/meraki_config_template.py b/lib/ansible/modules/network/meraki/meraki_config_template.py index cad07e12bc1..a18254671a3 100644 --- a/lib/ansible/modules/network/meraki/meraki_config_template.py +++ b/lib/ansible/modules/network/meraki/meraki_config_template.py @@ -154,30 +154,19 @@ def delete_template(meraki, org_id, name, data): return response -def bind(meraki, org_name, net_id, nets, name, data): - template_id = get_template_id(meraki, name, data) - if is_network_bound(meraki, nets, net_id, template_id) is False: - path = meraki.construct_path('bind', function='config_template', net_id=net_id) - payload = dict() - payload['configTemplateId'] = template_id - if meraki.params['auto_bind']: - payload['autoBind'] = meraki.params['auto_bind'] - meraki.result['changed'] = True - r = meraki.request(path, method='POST', payload=json.dumps(payload)) - if meraki.status != 200: - meraki.fail_json(msg='Unable to bind configuration template to network') - return r - - -def unbind(meraki, org_name, net_id, nets, name, data): - template_id = get_template_id(meraki, name, data) - if is_network_bound(meraki, nets, net_id, template_id) is True: - path = meraki.construct_path('unbind', function='config_template', net_id=net_id) - meraki.result['changed'] = True - r = meraki.request(path, method='POST') - if meraki.status != 200: - meraki.fail_json(msg='Unable to unbind configuration template from network') - return r +def bind(meraki, net_id, template_id): + path = meraki.construct_path('bind', net_id=net_id) + payload = {'configTemplateId': template_id} + if meraki.params['auto_bind']: + payload['autoBind'] = meraki.params['auto_bind'] + r = meraki.request(path, method='POST', payload=json.dumps(payload)) + return r + + +def unbind(meraki, net_id): + path = meraki.construct_path('unbind', net_id=net_id) + meraki.result['changed'] = True + return meraki.request(path, method='POST') def main(): @@ -213,19 +202,12 @@ def main(): meraki = MerakiModule(module, function='config_template') meraki.params['follow_redirects'] = 'all' - query_urls = {'config_template': '/organizations/{org_id}/configTemplates', - } - - delete_urls = {'config_template': '/organizations/{org_id}/configTemplates', - } - - bind_urls = {'config_template': '/networks/{net_id}/bind', - } - - unbind_urls = {'config_template': '/networks/{net_id}/unbind', - } + query_urls = {'config_template': '/organizations/{org_id}/configTemplates'} + delete_urls = {'config_template': '/organizations/{org_id}/configTemplates'} + bind_urls = {'config_template': '/networks/{net_id}/bind'} + unbind_urls = {'config_template': '/networks/{net_id}/unbind'} - meraki.url_catalog['get_all']['config_template'] = '/organizations/{org_id}/configTemplates' + meraki.url_catalog['get_all'].update(query_urls) meraki.url_catalog['delete'] = delete_urls meraki.url_catalog['bind'] = bind_urls meraki.url_catalog['unbind'] = unbind_urls @@ -254,26 +236,36 @@ def main(): if meraki.params['state'] == 'query': meraki.result['data'] = get_config_templates(meraki, org_id) elif meraki.params['state'] == 'present': - if meraki.params['net_name']: + template_id = get_template_id(meraki, + meraki.params['config_template'], + get_config_templates(meraki, org_id)) + if is_network_bound(meraki, nets, net_id, template_id) is False: template_bind = bind(meraki, - meraki.params['org_name'], net_id, - nets, - meraki.params['config_template'], - get_config_templates(meraki, org_id)) + template_id) + if meraki.status != 200: + meraki.fail_json(msg='Unable to bind configuration template to network') + meraki.result['changed'] = True + meraki.result['data'] = template_bind elif meraki.params['state'] == 'absent': - if not meraki.params['net_name']: + if not meraki.params['net_name'] and not meraki.params['net_id']: meraki.result['data'] = delete_template(meraki, org_id, meraki.params['config_template'], get_config_templates(meraki, org_id)) + if meraki.status == 200: + meraki.result['changed'] = True else: - config_unbind = unbind(meraki, - meraki.params['org_name'], - net_id, - nets, - meraki.params['config_template'], - get_config_templates(meraki, org_id)) + template_id = get_template_id(meraki, + meraki.params['config_template'], + get_config_templates(meraki, org_id)) + if is_network_bound(meraki, nets, net_id, template_id) is True: + config_unbind = unbind(meraki, + net_id) + if meraki.status != 200: + meraki.fail_json(msg='Unable to unbind configuration template from network') + meraki.result['changed'] = True + meraki.result['data'] = config_unbind # in the event of a successful module execution, you will want to # simple AnsibleModule.exit_json(), passing the key/value results diff --git a/test/integration/targets/meraki_config_template/tasks/main.yml b/test/integration/targets/meraki_config_template/tasks/main.yml index 4bec7d21deb..53c7a9ba425 100644 --- a/test/integration/targets/meraki_config_template/tasks/main.yml +++ b/test/integration/targets/meraki_config_template/tasks/main.yml @@ -4,26 +4,26 @@ # GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt) --- - block: - - name: Test an API key is provided - fail: - msg: Please define an API key - when: auth_key is not defined + # - name: Test an API key is provided + # fail: + # msg: Please define an API key + # when: auth_key is not defined - - name: Use an invalid domain - meraki_config_template: - auth_key: '{{ auth_key }}' - host: marrrraki.com - state: query - org_name: DevTestOrg - output_level: debug - delegate_to: localhost - register: invalid_domain - ignore_errors: yes + # - name: Use an invalid domain + # meraki_config_template: + # auth_key: '{{ auth_key }}' + # host: marrrraki.com + # state: query + # org_name: DevTestOrg + # output_level: debug + # delegate_to: localhost + # register: invalid_domain + # ignore_errors: yes - - name: Connection assertions - assert: - that: - - '"Failed to connect to" in invalid_domain.msg' + # - name: Connection assertions + # assert: + # that: + # - '"Failed to connect to" in invalid_domain.msg' - name: Query all configuration templates meraki_config_template: @@ -37,7 +37,7 @@ auth_key: '{{auth_key}}' state: absent org_name: DevTestOrg - config_template: DevConfigTemplateInvalid + config_template: FakeConfigTemplate register: deleted ignore_errors: yes @@ -54,13 +54,24 @@ type: appliance delegate_to: localhost + - name: Get network id + meraki_network: + auth_key: '{{auth_key}}' + state: query + org_name: '{{test_org_name}}' + net_name: '{{test_net_name}}' + register: net_info + + - set_fact: + net_id: '{{net_info.data.id}}' + - name: Bind a template to a network meraki_config_template: auth_key: '{{auth_key}}' state: present org_name: '{{ test_org_name }}' net_name: '{{ test_net_name }}' - config_template: DevConfigTemplate + config_template: '{{test_template_name}}' register: bind - assert: @@ -73,7 +84,7 @@ state: present org_name: '{{ test_org_name }}' net_name: '{{ test_net_name }}' - config_template: DevConfigTemplate + config_template: '{{test_template_name}}' register: bind_invalid ignore_errors: yes @@ -87,7 +98,7 @@ state: absent org_name: '{{ test_org_name }}' net_name: '{{ test_net_name }}' - config_template: DevConfigTemplate + config_template: '{{test_template_name}}' register: unbind - assert: @@ -100,13 +111,52 @@ state: absent org_name: '{{ test_org_name }}' net_name: '{{ test_net_name }}' - config_template: DevConfigTemplate + config_template: '{{test_template_name}}' register: unbind_invalid - assert: that: unbind_invalid.changed == False + - name: Bind a template to a network via id + meraki_config_template: + auth_key: '{{auth_key}}' + state: present + org_name: '{{test_org_name}}' + net_id: '{{net_id}}' + config_template: '{{test_template_name}}' + register: bind_id + + - assert: + that: + bind_id.changed == True + + - name: Bind a template to a network via id for idempotency + meraki_config_template: + auth_key: '{{auth_key}}' + state: present + org_name: '{{test_org_name}}' + net_id: '{{net_id}}' + config_template: '{{test_template_name}}' + register: bind_id_idempotent + + - assert: + that: + bind_id_idempotent.changed == False + + - name: Unbind a template to a network via id + meraki_config_template: + auth_key: '{{auth_key}}' + state: absent + org_name: '{{test_org_name}}' + net_id: '{{net_id}}' + config_template: '{{test_template_name}}' + register: unbind_id + + - assert: + that: + unbind_id.changed == True + always: - name: Delete network meraki_network: