diff --git a/lib/ansible/modules/network/nxos/nxos_bgp_neighbor.py b/lib/ansible/modules/network/nxos/nxos_bgp_neighbor.py index 65d5dce3f86..41ddf9cf4d5 100644 --- a/lib/ansible/modules/network/nxos/nxos_bgp_neighbor.py +++ b/lib/ansible/modules/network/nxos/nxos_bgp_neighbor.py @@ -53,6 +53,13 @@ options: description: description: - Description of the neighbor. + bfd: + description: + - Enables/Disables BFD for a given neighbor. + - "Dependency: 'feature bfd'" + version_added: "2.9" + type: str + choices: ['enable', 'disable'] connected_check: description: - Configure whether or not to check for directly connected peer. @@ -154,6 +161,7 @@ EXAMPLES = ''' neighbor: 192.0.2.3 local_as: 20 remote_as: 30 + bfd: enable description: "just a description" update_source: Ethernet1/3 state: present @@ -188,6 +196,7 @@ BOOL_PARAMS = [ ] PARAM_TO_COMMAND_KEYMAP = { 'asn': 'router bgp', + 'bfd': 'bfd', 'capability_negotiation': 'dont-capability-negotiate', 'connected_check': 'disable-connected-check', 'description': 'description', @@ -211,6 +220,7 @@ PARAM_TO_COMMAND_KEYMAP = { 'vrf': 'vrf' } PARAM_TO_DEFAULT_KEYMAP = { + 'bfd': 'disable', 'shutdown': False, 'dynamic_capability': True, 'timers_keepalive': 60, @@ -245,6 +255,8 @@ def get_value(arg, config): value = 'enable' elif has_command_val: value = has_command_val.group('value') + elif arg == 'bfd': + value = 'enable' if has_command else 'disable' else: value = '' @@ -354,6 +366,9 @@ def state_present(module, existing, proposed, candidate): proposed['timers_holdtime']) if command not in commands: commands.append(command) + elif key == 'bfd': + no_cmd = 'no ' if value == 'disable' else '' + commands.append(no_cmd + key) else: command = '{0} {1}'.format(key, value) commands.append(command) @@ -389,6 +404,7 @@ def main(): vrf=dict(required=False, type='str', default='default'), neighbor=dict(required=True, type='str'), description=dict(required=False, type='str'), + bfd=dict(required=False, type='str', choices=['enable', 'disable']), capability_negotiation=dict(required=False, type='bool'), connected_check=dict(required=False, type='bool'), dynamic_capability=dict(required=False, type='bool'), @@ -442,7 +458,10 @@ def main(): if key not in ['asn', 'vrf', 'neighbor', 'pwd_type']: if str(value).lower() == 'default': value = PARAM_TO_DEFAULT_KEYMAP.get(key, 'default') - if existing.get(key) != value: + if key == 'bfd': + if existing.get('bfd', 'disable') != value: + proposed[key] = value + elif existing.get(key) != value: proposed[key] = value candidate = CustomNetworkConfig(indent=3) diff --git a/test/integration/targets/nxos_bgp_neighbor/tests/common/sanity.yaml b/test/integration/targets/nxos_bgp_neighbor/tests/common/sanity.yaml index 686e20e2105..8f407ad0e6e 100644 --- a/test/integration/targets/nxos_bgp_neighbor/tests/common/sanity.yaml +++ b/test/integration/targets/nxos_bgp_neighbor/tests/common/sanity.yaml @@ -15,32 +15,20 @@ - set_fact: remove_private_asr="replace-as" when: not titanium -- name: "Enable feature BGP" +- name: "Setup: Disable features" nxos_feature: - feature: bgp + feature: "{{ item }}" + provider: "{{ connection }}" + state: disabled + loop: ['bgp', 'bfd'] + ignore_errors: yes + +- name: "Setup: Enable features" + nxos_feature: + feature: "{{ item }}" provider: "{{ connection }}" state: enabled - ignore_errors: yes - -- name: "Setup" - nxos_bgp_neighbor: &removenp - asn: 65535 - neighbor: 192.0.2.3 - vrf: "{{ item }}" - provider: "{{ connection }}" - state: absent - with_items: "{{ vrfs }}" - ignore_errors: yes - -- name: "Setup" - nxos_bgp_neighbor: &remove - asn: 65535 - neighbor: 192.0.2.3/32 - vrf: "{{ item }}" - provider: "{{ connection }}" - state: absent - with_items: "{{ vrfs }}" - ignore_errors: yes + loop: ['bgp', 'bfd'] - block: - name: "Configure BGP neighbor1" @@ -116,7 +104,12 @@ - assert: *false - name: "Remove BGP" - nxos_bgp_neighbor: *remove + nxos_bgp_neighbor: &remove + asn: 65535 + neighbor: 192.0.2.3/32 + vrf: "{{ item }}" + provider: "{{ connection }}" + state: absent with_items: "{{ vrfs }}" register: result @@ -291,7 +284,12 @@ - assert: *false - name: "Remove BGP" - nxos_bgp_neighbor: *removenp + nxos_bgp_neighbor: &removenp + asn: 65535 + neighbor: 192.0.2.3 + vrf: "{{ item }}" + provider: "{{ connection }}" + state: absent with_items: "{{ vrfs }}" register: result @@ -304,17 +302,47 @@ - assert: *false - rescue: - - name: "Cleanup BGP" - nxos_bgp_neighbor: *remove - with_items: "{{ vrfs }}" - ignore_errors: yes + - name: "Configure BFD enable" + nxos_bgp_neighbor: &bfd_enable + asn: 65535 + neighbor: 192.168.1.1 + bfd: enable + provider: "{{ connection }}" + state: present + register: result + + - assert: *true + + - name: Check BFD enable Idempotence + nxos_bgp_neighbor: *bfd_enable + register: result + + - assert: *false + + - name: Configure BFD disable Idempotence + nxos_bgp_neighbor: &bfd_disable + asn: 65535 + neighbor: 192.168.1.1 + bfd: disable + provider: "{{ connection }}" + state: present + register: result + + - assert: *true + + - name: Check BFD disable Idempotence + nxos_bgp_neighbor: *bfd_disable + register: result + + - assert: *false always: - - name: "Disable feature bgp" - nxos_feature: &disable_bgp - feature: bgp + - name: "Teardown: Disable features" + nxos_feature: + feature: "{{ item }}" provider: "{{ connection }}" state: disabled + loop: ['bgp', 'bfd'] + ignore_errors: yes - debug: msg="END connection={{ ansible_connection }} nxos_bgp_neighbor sanity test" diff --git a/test/units/modules/network/nxos/fixtures/nxos_bgp/config.cfg b/test/units/modules/network/nxos/fixtures/nxos_bgp/config.cfg index 728e8ea1ea3..2ef5533e422 100644 --- a/test/units/modules/network/nxos/fixtures/nxos_bgp/config.cfg +++ b/test/units/modules/network/nxos/fixtures/nxos_bgp/config.cfg @@ -7,6 +7,9 @@ router bgp 65535 vrf test2 address-family ipv4 unicast timers bgp 1 10 + neighbor 1.1.1.1 + neighbor 1.1.1.2 + bfd neighbor 3.3.3.4 remove-private-as all neighbor 3.3.3.5 diff --git a/test/units/modules/network/nxos/test_nxos_bgp_neighbor.py b/test/units/modules/network/nxos/test_nxos_bgp_neighbor.py index ac05f6120f2..564ef301e40 100644 --- a/test/units/modules/network/nxos/test_nxos_bgp_neighbor.py +++ b/test/units/modules/network/nxos/test_nxos_bgp_neighbor.py @@ -46,10 +46,32 @@ class TestNxosBgpNeighborModule(TestNxosModule): self.get_config.return_value = load_fixture('nxos_bgp', 'config.cfg') self.load_config.return_value = [] + def test_nxos_bgp_neighbor_bfd_1(self): + # None (disable) -> enable + set_module_args(dict(asn=65535, neighbor='1.1.1.1', bfd='enable')) + self.execute_module(changed=True, commands=['router bgp 65535', 'neighbor 1.1.1.1', 'bfd']) + + # enable -> enable (idempotence) + set_module_args(dict(asn=65535, neighbor='1.1.1.2', bfd='enable')) + self.execute_module(changed=False) + + def test_nxos_bgp_neighbor_bfd_2(self): + # enable -> None (disable) + set_module_args(dict(asn=65535, neighbor='1.1.1.2', bfd='disable')) + self.execute_module(changed=True, commands=['router bgp 65535', 'neighbor 1.1.1.2', 'no bfd']) + + # None (disable) -> disable (idempotence) + set_module_args(dict(asn=65535, neighbor='1.1.1.1', bfd='disable')) + self.execute_module(changed=False) + def test_nxos_bgp_neighbor(self): set_module_args(dict(asn=65535, neighbor='192.0.2.3', description='some words')) self.execute_module(changed=True, commands=['router bgp 65535', 'neighbor 192.0.2.3', 'description some words']) + def test_nxos_bgp_neighbor_absent(self): + set_module_args(dict(asn=65535, neighbor='1.1.1.1', state='absent')) + self.execute_module(changed=True, commands=['router bgp 65535', 'no neighbor 1.1.1.1']) + def test_nxos_bgp_neighbor_remove_private_as(self): set_module_args(dict(asn=65535, neighbor='3.3.3.4', remove_private_as='all')) self.execute_module(changed=False, commands=[])