From d43fb67583ad372b953b1b3dd1db55e6dc6c63de Mon Sep 17 00:00:00 2001 From: QijunPan Date: Thu, 25 May 2017 23:02:54 +0800 Subject: [PATCH] Contributing lib/ansible/modules/network/cloudengine/ce_bgp_neighbor.py module to manage HUAWEI data center CloudEngine (#22032) * add ce_bgp_neighbor add ce_bgp_neighbor * fix review issues --- .../network/cloudengine/ce_bgp_neighbor.py | 2101 +++++++++++++++++ 1 file changed, 2101 insertions(+) create mode 100644 lib/ansible/modules/network/cloudengine/ce_bgp_neighbor.py diff --git a/lib/ansible/modules/network/cloudengine/ce_bgp_neighbor.py b/lib/ansible/modules/network/cloudengine/ce_bgp_neighbor.py new file mode 100644 index 00000000000..92caa9d6c01 --- /dev/null +++ b/lib/ansible/modules/network/cloudengine/ce_bgp_neighbor.py @@ -0,0 +1,2101 @@ +#!/usr/bin/python +# +# This file is part of Ansible +# +# Ansible is free software: you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation, either version 3 of the License, or +# (at your option) any later version. +# +# Ansible is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with Ansible. If not, see . +# + +ANSIBLE_METADATA = {'status': ['preview'], + 'supported_by': 'community', + 'metadata_version': '1.0'} + +DOCUMENTATION = ''' +--- +module: ce_bgp_neighbor +version_added: "2.4" +short_description: Manages BGP peer configuration on HUAWEI CloudEngine switches. +description: + - Manages BGP peer configurations on HUAWEI CloudEngine switches. +author: + - wangdezhuang (@CloudEngine-Ansible) +options: + state: + description: + - Specify desired state of the resource. + required: false + default: present + choices: ['present','absent'] + vrf_name: + description: + - Name of a BGP instance. The name is a case-sensitive string of characters. + The BGP instance can be used only after the corresponding VPN instance is created. + required: true + peer_addr: + description: + - Connection address of a peer, which can be an IPv4 or IPv6 address. + required: true + remote_as: + description: + - AS number of a peer. + The value is a string of 1 to 11 characters. + required: true + description: + description: + - Description of a peer, which can be letters or digits. + The value is a string of 1 to 80 characters. + required: false + default: null + fake_as: + description: + - Fake AS number that is specified for a local peer. + The value is a string of 1 to 11 characters. + required: false + default: null + dual_as: + description: + - If the value is true, the EBGP peer can use either a fake AS number or the actual AS number. + If the value is false, the EBGP peer can only use a fake AS number. + required: false + choices: ['no_use','true','false'] + default: no_use + conventional: + description: + - If the value is true, the router has all extended capabilities. + If the value is false, the router does not have all extended capabilities. + required: false + choices: ['no_use','true','false'] + default: no_use + route_refresh: + description: + - If the value is true, BGP is enabled to advertise REFRESH packets. + If the value is false, the route refresh function is enabled. + required: false + choices: ['no_use','true','false'] + default: no_use + is_ignore: + description: + - If the value is true, the session with a specified peer is torn down and all related + routing entries are cleared. + If the value is false, the session with a specified peer is retained. + required: false + choices: ['no_use','true','false'] + default: no_use + local_if_name: + description: + - Name of a source interface that sends BGP packets. + The value is a string of 1 to 63 characters. + required: false + default: null + ebgp_max_hop: + description: + - Maximum number of hops in an indirect EBGP connection. + The value is an ranging from 1 to 255. + required: false + default: null + valid_ttl_hops: + description: + - Enable GTSM on a peer or peer group. + The valid-TTL-Value parameter is used to specify the number of TTL hops to be detected. + The value is an integer ranging from 1 to 255. + required: false + default: null + connect_mode: + description: + - The value can be Connect-only, Listen-only, or Both. + required: false + default: null + is_log_change: + description: + - If the value is true, BGP is enabled to record peer session status and event information. + If the value is false, BGP is disabled from recording peer session status and event information. + required: false + choices: ['no_use','true','false'] + default: no_use + pswd_type: + description: + - Enable BGP peers to establish a TCP connection and perform the Message Digest 5 (MD5) + authentication for BGP messages. + required: false + choices: ['null','cipher','simple'] + default: null + pswd_cipher_text: + description: + - The character string in a password identifies the contents of the password, spaces not supported. + The value is a string of 1 to 255 characters. + required: false + default: null + keep_alive_time: + description: + - Specify the Keepalive time of a peer or peer group. + The value is an integer ranging from 0 to 21845. The default value is 60. + required: false + default: null + hold_time: + description: + - Specify the Hold time of a peer or peer group. + The value is 0 or an integer ranging from 3 to 65535. + required: false + default: null + min_hold_time: + description: + - Specify the Min hold time of a peer or peer group. + required: false + default: null + key_chain_name: + description: + - Specify the Keychain authentication name used when BGP peers establish a TCP connection. + The value is a string of 1 to 47 case-insensitive characters. + required: false + default: null + conn_retry_time: + description: + - ConnectRetry interval. + The value is an integer ranging from 1 to 65535. + required: false + default: null + tcp_MSS: + description: + - Maximum TCP MSS value used for TCP connection establishment for a peer. + The value is an integer ranging from 176 to 4096. + required: false + default: null + mpls_local_ifnet_disable: + description: + - If the value is true, peer create MPLS Local IFNET disable. + If the value is false, peer create MPLS Local IFNET enable. + required: false + choices: ['no_use','true','false'] + default: no_use + prepend_global_as: + description: + - Add the global AS number to the Update packets to be advertised. + required: false + choices: ['no_use','true','false'] + default: no_use + prepend_fake_as: + description: + - Add the Fake AS number to received Update packets. + required: false + choices: ['no_use','true','false'] + default: no_use + is_bfd_block: + description: + - If the value is true, peers are enabled to inherit the BFD function from the peer group. + If the value is false, peers are disabled to inherit the BFD function from the peer group. + required: false + choices: ['no_use','true','false'] + default: no_use + multiplier: + description: + - Specify the detection multiplier. The default value is 3. + The value is an integer ranging from 3 to 50. + required: false + default: null + is_bfd_enable: + description: + - If the value is true, BFD is enabled. + If the value is false, BFD is disabled. + required: false + choices: ['no_use','true','false'] + default: no_use + rx_interval: + description: + - Specify the minimum interval at which BFD packets are received. + The value is an integer ranging from 50 to 1000, in milliseconds. + required: false + default: null + tx_interval: + description: + - Specify the minimum interval at which BFD packets are sent. + The value is an integer ranging from 50 to 1000, in milliseconds. + required: false + default: null + is_single_hop: + description: + - If the value is true, the system is enabled to preferentially use the single-hop mode for + BFD session setup between IBGP peers. + If the value is false, the system is disabled from preferentially using the single-hop + mode for BFD session setup between IBGP peers. + required: false + choices: ['no_use','true','false'] + default: no_use +''' + +EXAMPLES = ''' + +- name: CloudEngine BGP neighbor test + hosts: cloudengine + connection: local + gather_facts: no + vars: + cli: + host: "{{ inventory_hostname }}" + port: "{{ ansible_ssh_port }}" + username: "{{ username }}" + password: "{{ password }}" + transport: cli + + tasks: + + - name: "Config bgp peer" + ce_bgp_neighbor: + state: present + vrf_name: js + peer_addr: 192.168.10.10 + remote_as: 500 + provider: "{{ cli }}" + + - name: "Config bgp route id" + ce_bgp_neighbor: + state: absent + vrf_name: js + peer_addr: 192.168.10.10 + provider: "{{ cli }}" +''' + +RETURN = ''' +changed: + description: check to see if a change was made on the device + returned: always + type: boolean + sample: true +proposed: + description: k/v pairs of parameters passed into module + returned: always + type: dict + sample: {"peer_addr": "192.168.10.10", "remote_as": "500", "state": "present", "vrf_name": "js"} +existing: + description: k/v pairs of existing aaa server + returned: always + type: dict + sample: {"bgp peer": []} +end_state: + description: k/v pairs of aaa params after module execution + returned: always + type: dict + sample: {"bgp peer": [["192.168.10.10", "500"]]} +updates: + description: command sent to the device + returned: always + type: list + sample: ["peer 192.168.10.10 as-number 500"] +''' + +import re +import sys +import socket +from ansible.module_utils.basic import AnsibleModule +from ansible.module_utils.ce import get_nc_config, set_nc_config, ce_argument_spec + + +# get bgp peer +CE_GET_BGP_PEER_HEADER = """ + + + + + + %s + + + +""" +CE_GET_BGP_PEER_TAIL = """ + + + + + + + +""" + + +# merge bgp peer +CE_MERGE_BGP_PEER_HEADER = """ + + + + + + %s + + + %s +""" +CE_MERGE_BGP_PEER_TAIL = """ + + + + + + + +""" + +# create bgp peer +CE_CREATE_BGP_PEER_HEADER = """ + + + + + + %s + + + %s +""" +CE_CREATE_BGP_PEER_TAIL = """ + + + + + + + +""" + +# delete bgp peer +CE_DELETE_BGP_PEER_HEADER = """ + + + + + + %s + + + %s +""" +CE_DELETE_BGP_PEER_TAIL = """ + + + + + + + +""" + +# get peer bfd +CE_GET_PEER_BFD_HEADER = """ + + + + + + %s + + + %s + +""" +CE_GET_PEER_BFD_TAIL = """ + + + + + + + + +""" + +# merge peer bfd +CE_MERGE_PEER_BFD_HEADER = """ + + + + + + %s + + + %s + +""" +CE_MERGE_PEER_BFD_TAIL = """ + + + + + + + + +""" + +# delete peer bfd +CE_DELETE_PEER_BFD_HEADER = """ + + + + + + %s + + + %s + +""" +CE_DELETE_PEER_BFD_TAIL = """ + + + + + + + + +""" + + +def check_ip_addr(**kwargs): + """ check_ip_addr, Supports IPv4 and IPv6 """ + + ipaddr = kwargs["ipaddr"] + + if not ipaddr or '\x00' in ipaddr: + return False + + try: + res = socket.getaddrinfo(ipaddr, 0, socket.AF_UNSPEC, + socket.SOCK_STREAM, + 0, socket.AI_NUMERICHOST) + return bool(res) + except socket.gaierror: + err = sys.exc_info()[1] + if err.args[0] == socket.EAI_NONAME: + return False + raise + return True + + +class BgpNeighbor(object): + """ Manages BGP peer configuration """ + + def netconf_get_config(self, **kwargs): + """ netconf_get_config """ + + module = kwargs["module"] + conf_str = kwargs["conf_str"] + + xml_str = get_nc_config(module, conf_str) + + return xml_str + + def netconf_set_config(self, **kwargs): + """ netconf_set_config """ + + module = kwargs["module"] + conf_str = kwargs["conf_str"] + + xml_str = set_nc_config(module, conf_str) + + return xml_str + + def check_bgp_peer_args(self, **kwargs): + """ check_bgp_peer_args """ + + module = kwargs["module"] + result = dict() + need_cfg = False + + vrf_name = module.params['vrf_name'] + if vrf_name: + if len(vrf_name) > 31 or len(vrf_name) == 0: + module.fail_json( + msg='Error: The len of vrf_name %s is out of [1 - 31].' % vrf_name) + + peer_addr = module.params['peer_addr'] + if peer_addr: + if not check_ip_addr(ipaddr=peer_addr): + module.fail_json( + msg='Error: The peer_addr %s is invalid.' % peer_addr) + + need_cfg = True + + remote_as = module.params['remote_as'] + if remote_as: + if len(remote_as) > 11 or len(remote_as) < 1: + module.fail_json( + msg='Error: The len of remote_as %s is out of [1 - 11].' % remote_as) + + need_cfg = True + + result["need_cfg"] = need_cfg + return result + + def check_bgp_peer_other_args(self, **kwargs): + """ check_bgp_peer_other_args """ + + module = kwargs["module"] + result = dict() + need_cfg = False + + vrf_name = module.params['vrf_name'] + if vrf_name: + if len(vrf_name) > 31 or len(vrf_name) == 0: + module.fail_json( + msg='Error: The len of vrf_name %s is out of [1 - 31].' % vrf_name) + + description = module.params['description'] + if description: + if len(description) > 80 or len(description) < 1: + module.fail_json( + msg='Error: The len of description %s is out of [1 - 80].' % description) + + conf_str = CE_GET_BGP_PEER_HEADER % vrf_name + \ + "" + CE_GET_BGP_PEER_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["description"] = re_find + if re_find[0] != description: + need_cfg = True + else: + need_cfg = True + + fake_as = module.params['fake_as'] + if fake_as: + if len(fake_as) > 11 or len(fake_as) < 1: + module.fail_json( + msg='Error: The len of fake_as %s is out of [1 - 11].' % fake_as) + + conf_str = CE_GET_BGP_PEER_HEADER % vrf_name + \ + "" + CE_GET_BGP_PEER_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["fake_as"] = re_find + if re_find[0] != fake_as: + need_cfg = True + else: + need_cfg = True + + dual_as = module.params['dual_as'] + if dual_as != 'no_use': + + conf_str = CE_GET_BGP_PEER_HEADER % vrf_name + \ + "" + CE_GET_BGP_PEER_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["dual_as"] = re_find + if re_find[0] != fake_as: + need_cfg = True + else: + need_cfg = True + + conventional = module.params['conventional'] + if conventional != 'no_use': + + conf_str = CE_GET_BGP_PEER_HEADER % vrf_name + \ + "" + CE_GET_BGP_PEER_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["conventional"] = re_find + if re_find[0] != conventional: + need_cfg = True + else: + need_cfg = True + + route_refresh = module.params['route_refresh'] + if route_refresh != 'no_use': + + conf_str = CE_GET_BGP_PEER_HEADER % vrf_name + \ + "" + CE_GET_BGP_PEER_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["route_refresh"] = re_find + if re_find[0] != route_refresh: + need_cfg = True + else: + need_cfg = True + + four_byte_as = module.params['four_byte_as'] + if four_byte_as != 'no_use': + + conf_str = CE_GET_BGP_PEER_HEADER % vrf_name + \ + "" + CE_GET_BGP_PEER_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["four_byte_as"] = re_find + if re_find[0] != four_byte_as: + need_cfg = True + else: + need_cfg = True + + is_ignore = module.params['is_ignore'] + if is_ignore != 'no_use': + + conf_str = CE_GET_BGP_PEER_HEADER % vrf_name + \ + "" + CE_GET_BGP_PEER_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["is_ignore"] = re_find + if re_find[0] != is_ignore: + need_cfg = True + else: + need_cfg = True + + local_if_name = module.params['local_if_name'] + if local_if_name: + if len(local_if_name) > 63 or len(local_if_name) < 1: + module.fail_json( + msg='Error: The len of local_if_name %s is out of [1 - 63].' % local_if_name) + + conf_str = CE_GET_BGP_PEER_HEADER % vrf_name + \ + "" + CE_GET_BGP_PEER_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["local_if_name"] = re_find + if re_find[0] != local_if_name: + need_cfg = True + else: + need_cfg = True + + ebgp_max_hop = module.params['ebgp_max_hop'] + if ebgp_max_hop: + if int(ebgp_max_hop) > 255 or int(ebgp_max_hop) < 1: + module.fail_json( + msg='Error: The value of ebgp_max_hop %s is out of [1 - 255].' % ebgp_max_hop) + + conf_str = CE_GET_BGP_PEER_HEADER % vrf_name + \ + "" + CE_GET_BGP_PEER_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["ebgp_max_hop"] = re_find + if re_find[0] != ebgp_max_hop: + need_cfg = True + else: + need_cfg = True + + valid_ttl_hops = module.params['valid_ttl_hops'] + if valid_ttl_hops: + if int(valid_ttl_hops) > 255 or int(valid_ttl_hops) < 1: + module.fail_json( + msg='Error: The value of valid_ttl_hops %s is out of [1 - 255].' % valid_ttl_hops) + + conf_str = CE_GET_BGP_PEER_HEADER % vrf_name + \ + "" + CE_GET_BGP_PEER_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["valid_ttl_hops"] = re_find + if re_find[0] != valid_ttl_hops: + need_cfg = True + else: + need_cfg = True + + connect_mode = module.params['connect_mode'] + if connect_mode: + + conf_str = CE_GET_BGP_PEER_HEADER % vrf_name + \ + "" + CE_GET_BGP_PEER_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["connect_mode"] = re_find + if re_find[0] != connect_mode: + need_cfg = True + else: + need_cfg = True + + is_log_change = module.params['is_log_change'] + if is_log_change != 'no_use': + + conf_str = CE_GET_BGP_PEER_HEADER % vrf_name + \ + "" + CE_GET_BGP_PEER_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["is_log_change"] = re_find + if re_find[0] != is_log_change: + need_cfg = True + else: + need_cfg = True + + pswd_type = module.params['pswd_type'] + if pswd_type: + + conf_str = CE_GET_BGP_PEER_HEADER % vrf_name + \ + "" + CE_GET_BGP_PEER_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["pswd_type"] = re_find + if re_find[0] != pswd_type: + need_cfg = True + else: + need_cfg = True + + pswd_cipher_text = module.params['pswd_cipher_text'] + if pswd_cipher_text: + if len(pswd_cipher_text) > 255 or len(pswd_cipher_text) < 1: + module.fail_json( + msg='Error: The len of pswd_cipher_text %s is out of [1 - 255].' % pswd_cipher_text) + + conf_str = CE_GET_BGP_PEER_HEADER % vrf_name + \ + "" + CE_GET_BGP_PEER_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["pswd_cipher_text"] = re_find + if re_find[0] != pswd_cipher_text: + need_cfg = True + else: + need_cfg = True + + keep_alive_time = module.params['keep_alive_time'] + if keep_alive_time: + if int(keep_alive_time) > 21845 or len(keep_alive_time) < 0: + module.fail_json( + msg='Error: The len of keep_alive_time %s is out of [0 - 21845].' % keep_alive_time) + + conf_str = CE_GET_BGP_PEER_HEADER % vrf_name + \ + "" + CE_GET_BGP_PEER_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["keep_alive_time"] = re_find + if re_find[0] != keep_alive_time: + need_cfg = True + else: + need_cfg = True + + hold_time = module.params['hold_time'] + if hold_time: + if int(hold_time) != 0 and (int(hold_time) > 65535 or int(hold_time) < 3): + module.fail_json( + msg='Error: The value of hold_time %s is out of [0 or 3 - 65535].' % hold_time) + + conf_str = CE_GET_BGP_PEER_HEADER % vrf_name + \ + "" + CE_GET_BGP_PEER_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["hold_time"] = re_find + if re_find[0] != hold_time: + need_cfg = True + else: + need_cfg = True + + min_hold_time = module.params['min_hold_time'] + if min_hold_time: + if int(min_hold_time) != 0 and (int(min_hold_time) > 65535 or int(min_hold_time) < 20): + module.fail_json( + msg='Error: The value of min_hold_time %s is out of [0 or 20 - 65535].' % min_hold_time) + + conf_str = CE_GET_BGP_PEER_HEADER % vrf_name + \ + "" + CE_GET_BGP_PEER_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["min_hold_time"] = re_find + if re_find[0] != min_hold_time: + need_cfg = True + else: + need_cfg = True + + key_chain_name = module.params['key_chain_name'] + if key_chain_name: + if len(key_chain_name) > 47 or len(key_chain_name) < 1: + module.fail_json( + msg='Error: The len of key_chain_name %s is out of [1 - 47].' % key_chain_name) + + conf_str = CE_GET_BGP_PEER_HEADER % vrf_name + \ + "" + CE_GET_BGP_PEER_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["key_chain_name"] = re_find + if re_find[0] != key_chain_name: + need_cfg = True + else: + need_cfg = True + + conn_retry_time = module.params['conn_retry_time'] + if conn_retry_time: + if int(conn_retry_time) > 65535 or int(conn_retry_time) < 1: + module.fail_json( + msg='Error: The value of conn_retry_time %s is out of [1 - 65535].' % conn_retry_time) + + conf_str = CE_GET_BGP_PEER_HEADER % vrf_name + \ + "" + CE_GET_BGP_PEER_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["conn_retry_time"] = re_find + if re_find[0] != conn_retry_time: + need_cfg = True + else: + need_cfg = True + + tcp_mss = module.params['tcp_MSS'] + if tcp_mss: + if int(tcp_mss) > 4096 or int(tcp_mss) < 176: + module.fail_json( + msg='Error: The value of tcp_mss %s is out of [176 - 4096].' % tcp_mss) + + conf_str = CE_GET_BGP_PEER_HEADER % vrf_name + \ + "" + CE_GET_BGP_PEER_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["tcp_MSS"] = re_find + if re_find[0] != tcp_mss: + need_cfg = True + else: + need_cfg = True + + mpls_local_ifnet_disable = module.params['mpls_local_ifnet_disable'] + if mpls_local_ifnet_disable != 'no_use': + + conf_str = CE_GET_BGP_PEER_HEADER % vrf_name + \ + "" + CE_GET_BGP_PEER_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["mpls_local_ifnet_disable"] = re_find + if re_find[0] != mpls_local_ifnet_disable: + need_cfg = True + else: + need_cfg = True + + prepend_global_as = module.params['prepend_global_as'] + if prepend_global_as != 'no_use': + + conf_str = CE_GET_BGP_PEER_HEADER % vrf_name + \ + "" + CE_GET_BGP_PEER_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["prepend_global_as"] = re_find + if re_find[0] != prepend_global_as: + need_cfg = True + else: + need_cfg = True + + prepend_fake_as = module.params['prepend_fake_as'] + if prepend_fake_as != 'no_use': + + conf_str = CE_GET_BGP_PEER_HEADER % vrf_name + \ + "" + CE_GET_BGP_PEER_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["prepend_fake_as"] = re_find + if re_find[0] != prepend_fake_as: + need_cfg = True + else: + need_cfg = True + + result["need_cfg"] = need_cfg + return result + + def check_peer_bfd_merge_args(self, **kwargs): + """ check_peer_bfd_merge_args """ + + module = kwargs["module"] + result = dict() + need_cfg = False + + state = module.params['state'] + if state == "absent": + result["need_cfg"] = need_cfg + return result + + vrf_name = module.params['vrf_name'] + if vrf_name: + if len(vrf_name) > 31 or len(vrf_name) == 0: + module.fail_json( + msg='Error: The len of vrf_name %s is out of [1 - 31].' % vrf_name) + + peer_addr = module.params['peer_addr'] + + is_bfd_block = module.params['is_bfd_block'] + if is_bfd_block != 'no_use': + + conf_str = CE_GET_PEER_BFD_HEADER % ( + vrf_name, peer_addr) + "" + CE_GET_PEER_BFD_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["is_bfd_block"] = re_find + if re_find[0] != is_bfd_block: + need_cfg = True + else: + need_cfg = True + + multiplier = module.params['multiplier'] + if multiplier: + if int(multiplier) > 50 or int(multiplier) < 3: + module.fail_json( + msg='Error: The value of multiplier %s is out of [3 - 50].' % multiplier) + + conf_str = CE_GET_PEER_BFD_HEADER % ( + vrf_name, peer_addr) + "" + CE_GET_PEER_BFD_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["multiplier"] = re_find + if re_find[0] != multiplier: + need_cfg = True + else: + need_cfg = True + + is_bfd_enable = module.params['is_bfd_enable'] + if is_bfd_enable != 'no_use': + + conf_str = CE_GET_PEER_BFD_HEADER % ( + vrf_name, peer_addr) + "" + CE_GET_PEER_BFD_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["is_bfd_enable"] = re_find + if re_find[0] != is_bfd_enable: + need_cfg = True + else: + need_cfg = True + + rx_interval = module.params['rx_interval'] + if rx_interval: + if int(rx_interval) > 1000 or int(rx_interval) < 50: + module.fail_json( + msg='Error: The value of rx_interval %s is out of [50 - 1000].' % rx_interval) + + conf_str = CE_GET_PEER_BFD_HEADER % ( + vrf_name, peer_addr) + "" + CE_GET_PEER_BFD_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["rx_interval"] = re_find + if re_find[0] != rx_interval: + need_cfg = True + else: + need_cfg = True + + tx_interval = module.params['tx_interval'] + if tx_interval: + if int(tx_interval) > 1000 or int(tx_interval) < 50: + module.fail_json( + msg='Error: The value of tx_interval %s is out of [50 - 1000].' % tx_interval) + + conf_str = CE_GET_PEER_BFD_HEADER % ( + vrf_name, peer_addr) + "" + CE_GET_PEER_BFD_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["tx_interval"] = re_find + if re_find[0] != tx_interval: + need_cfg = True + else: + need_cfg = True + + is_single_hop = module.params['is_single_hop'] + if is_single_hop != 'no_use': + + conf_str = CE_GET_PEER_BFD_HEADER % ( + vrf_name, peer_addr) + "" + CE_GET_PEER_BFD_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + need_cfg = True + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["is_single_hop"] = re_find + if re_find[0] != is_single_hop: + need_cfg = True + else: + need_cfg = True + + result["need_cfg"] = need_cfg + return result + + def check_peer_bfd_delete_args(self, **kwargs): + """ check_peer_bfd_delete_args """ + + module = kwargs["module"] + result = dict() + need_cfg = False + + state = module.params['state'] + if state == "present": + result["need_cfg"] = need_cfg + return result + + vrf_name = module.params['vrf_name'] + if vrf_name: + if len(vrf_name) > 31 or len(vrf_name) == 0: + module.fail_json( + msg='Error: The len of vrf_name %s is out of [1 - 31].' % vrf_name) + + peer_addr = module.params['peer_addr'] + + is_bfd_block = module.params['is_bfd_block'] + if is_bfd_block != 'no_use': + + conf_str = CE_GET_PEER_BFD_HEADER % ( + vrf_name, peer_addr) + "" + CE_GET_PEER_BFD_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + pass + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["is_bfd_block"] = re_find + if re_find[0] == is_bfd_block: + need_cfg = True + + multiplier = module.params['multiplier'] + if multiplier: + if int(multiplier) > 50 or int(multiplier) < 3: + module.fail_json( + msg='Error: The value of multiplier %s is out of [3 - 50].' % multiplier) + + conf_str = CE_GET_PEER_BFD_HEADER % ( + vrf_name, peer_addr) + "" + CE_GET_PEER_BFD_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + pass + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["multiplier"] = re_find + if re_find[0] == multiplier: + need_cfg = True + + is_bfd_enable = module.params['is_bfd_enable'] + if is_bfd_enable != 'no_use': + + conf_str = CE_GET_PEER_BFD_HEADER % ( + vrf_name, peer_addr) + "" + CE_GET_PEER_BFD_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + pass + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["is_bfd_enable"] = re_find + if re_find[0] == is_bfd_enable: + need_cfg = True + + rx_interval = module.params['rx_interval'] + if rx_interval: + if int(rx_interval) > 1000 or int(rx_interval) < 50: + module.fail_json( + msg='Error: The value of rx_interval %s is out of [50 - 1000].' % rx_interval) + + conf_str = CE_GET_PEER_BFD_HEADER % ( + vrf_name, peer_addr) + "" + CE_GET_PEER_BFD_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + pass + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["rx_interval"] = re_find + if re_find[0] == rx_interval: + need_cfg = True + + tx_interval = module.params['tx_interval'] + if tx_interval: + if int(tx_interval) > 1000 or int(tx_interval) < 50: + module.fail_json( + msg='Error: The value of tx_interval %s is out of [50 - 1000].' % tx_interval) + + conf_str = CE_GET_PEER_BFD_HEADER % ( + vrf_name, peer_addr) + "" + CE_GET_PEER_BFD_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + pass + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["tx_interval"] = re_find + if re_find[0] == tx_interval: + need_cfg = True + + is_single_hop = module.params['is_single_hop'] + if is_single_hop != 'no_use': + + conf_str = CE_GET_PEER_BFD_HEADER % ( + vrf_name, peer_addr) + "" + CE_GET_PEER_BFD_TAIL + recv_xml = self.netconf_get_config(module=module, conf_str=conf_str) + + if "" in recv_xml: + pass + else: + re_find = re.findall( + r'.*(.*).*', recv_xml) + + if re_find: + result["is_single_hop"] = re_find + if re_find[0] == is_single_hop: + need_cfg = True + + result["need_cfg"] = need_cfg + return result + + def get_bgp_peer(self, **kwargs): + """ get_bgp_peer """ + + module = kwargs["module"] + + vrf_name = module.params['vrf_name'] + if vrf_name: + if len(vrf_name) > 31 or len(vrf_name) == 0: + module.fail_json( + msg='Error: The len of vrf_name %s is out of [1 - 31].' % vrf_name) + + conf_str = CE_GET_BGP_PEER_HEADER % vrf_name + \ + "" + CE_GET_BGP_PEER_TAIL + + xml_str = self.netconf_get_config(module=module, conf_str=conf_str) + + result = list() + + if "" in xml_str: + return result + else: + re_find = re.findall( + r'.*(.*).*\s.*(.*).*', xml_str) + + if re_find: + return re_find + else: + return result + + def get_bgp_del_peer(self, **kwargs): + """ get_bgp_del_peer """ + + module = kwargs["module"] + + vrf_name = module.params['vrf_name'] + if vrf_name: + if len(vrf_name) > 31 or len(vrf_name) == 0: + module.fail_json( + msg='Error: The len of vrf_name %s is out of [1 - 31].' % vrf_name) + + conf_str = CE_GET_BGP_PEER_HEADER % vrf_name + CE_GET_BGP_PEER_TAIL + + xml_str = self.netconf_get_config(module=module, conf_str=conf_str) + + result = list() + + if "" in xml_str: + return result + else: + re_find = re.findall( + r'.*(.*).*', xml_str) + + if re_find: + return re_find + else: + return result + + def merge_bgp_peer(self, **kwargs): + """ merge_bgp_peer """ + + module = kwargs["module"] + vrf_name = module.params['vrf_name'] + peer_addr = module.params['peer_addr'] + remote_as = module.params['remote_as'] + + conf_str = CE_MERGE_BGP_PEER_HEADER % ( + vrf_name, peer_addr) + "%s" % remote_as + CE_MERGE_BGP_PEER_TAIL + + recv_xml = self.netconf_set_config(module=module, conf_str=conf_str) + + if "" not in recv_xml: + module.fail_json(msg='Error: Merge bgp peer failed.') + + cmds = [] + cmd = "peer %s as-number %s" % (peer_addr, remote_as) + cmds.append(cmd) + + return cmds + + def create_bgp_peer(self, **kwargs): + """ create_bgp_peer """ + + module = kwargs["module"] + + vrf_name = module.params['vrf_name'] + + peer_addr = module.params['peer_addr'] + remote_as = module.params['remote_as'] + + conf_str = CE_CREATE_BGP_PEER_HEADER % ( + vrf_name, peer_addr) + "%s" % remote_as + CE_CREATE_BGP_PEER_TAIL + + recv_xml = self.netconf_set_config(module=module, conf_str=conf_str) + + if "" not in recv_xml: + module.fail_json(msg='Error: Create bgp peer failed.') + + cmds = [] + cmd = "peer %s as-number %s" % (peer_addr, remote_as) + cmds.append(cmd) + + return cmds + + def delete_bgp_peer(self, **kwargs): + """ delete_bgp_peer """ + + module = kwargs["module"] + vrf_name = module.params['vrf_name'] + peer_addr = module.params['peer_addr'] + + conf_str = CE_DELETE_BGP_PEER_HEADER % ( + vrf_name, peer_addr) + CE_DELETE_BGP_PEER_TAIL + + recv_xml = self.netconf_set_config(module=module, conf_str=conf_str) + + if "" not in recv_xml: + module.fail_json(msg='Error: Delete bgp peer failed.') + + cmds = [] + cmd = "undo peer %s" % peer_addr + cmds.append(cmd) + + return cmds + + def merge_bgp_peer_other(self, **kwargs): + """ merge_bgp_peer """ + + module = kwargs["module"] + vrf_name = module.params['vrf_name'] + peer_addr = module.params['peer_addr'] + + conf_str = CE_MERGE_BGP_PEER_HEADER % (vrf_name, peer_addr) + + cmds = [] + + description = module.params['description'] + if description: + conf_str += "%s" % description + + cmd = "peer %s description %s" % (peer_addr, description) + cmds.append(cmd) + + fake_as = module.params['fake_as'] + if fake_as: + conf_str += "%s" % fake_as + + cmd = "peer %s local-as %s" % (peer_addr, fake_as) + cmds.append(cmd) + + dual_as = module.params['dual_as'] + if dual_as != 'no_use': + conf_str += "%s" % dual_as + + if dual_as == "true": + cmd = "peer %s local-as %s dual-as" % (peer_addr, fake_as) + else: + cmd = "peer %s local-as %s" % (peer_addr, fake_as) + cmds.append(cmd) + + conventional = module.params['conventional'] + if conventional != 'no_use': + conf_str += "%s" % conventional + + if conventional == "true": + cmd = "peer %s capability-advertise conventional" % peer_addr + else: + cmd = "undo peer %s capability-advertise conventional" % peer_addr + cmds.append(cmd) + + route_refresh = module.params['route_refresh'] + if route_refresh != 'no_use': + conf_str += "%s" % route_refresh + + if route_refresh == "true": + cmd = "peer %s capability-advertise route-refresh" % peer_addr + else: + cmd = "undo peer %s capability-advertise route-refresh" % peer_addr + cmds.append(cmd) + + four_byte_as = module.params['four_byte_as'] + if four_byte_as != 'no_use': + conf_str += "%s" % four_byte_as + + if four_byte_as == "true": + cmd = "peer %s capability-advertise 4-byte-as" % peer_addr + else: + cmd = "undo peer %s capability-advertise 4-byte-as" % peer_addr + cmds.append(cmd) + + is_ignore = module.params['is_ignore'] + if is_ignore != 'no_use': + conf_str += "%s" % is_ignore + + if is_ignore == "true": + cmd = "peer %s ignore" % peer_addr + else: + cmd = "undo peer %s ignore" % peer_addr + cmds.append(cmd) + + local_if_name = module.params['local_if_name'] + if local_if_name: + conf_str += "%s" % local_if_name + + cmd = "peer %s connect-interface local_if_name" % peer_addr + cmds.append(cmd) + + ebgp_max_hop = module.params['ebgp_max_hop'] + if ebgp_max_hop: + conf_str += "%s" % ebgp_max_hop + + cmd = "peer %s ebgp-max-hop %s" % (peer_addr, ebgp_max_hop) + cmds.append(cmd) + + valid_ttl_hops = module.params['valid_ttl_hops'] + if valid_ttl_hops: + conf_str += "%s" % valid_ttl_hops + + cmd = "peer %s valid-ttl-hops %s" % (peer_addr, valid_ttl_hops) + cmds.append(cmd) + + connect_mode = module.params['connect_mode'] + if connect_mode: + conf_str += "%s" % connect_mode + + if connect_mode == "listenOnly": + cmd = "peer %s listen-only" % peer_addr + cmds.append(cmd) + elif connect_mode == "connectOnly": + cmd = "peer %s connect-only" % peer_addr + cmds.append(cmd) + elif connect_mode == "null": + cmd = "peer %s listen-only" % peer_addr + cmds.append(cmd) + cmd = "peer %s connect-only" % peer_addr + cmds.append(cmd) + + is_log_change = module.params['is_log_change'] + if is_log_change != 'no_use': + conf_str += "%s" % is_log_change + + if is_log_change == "true": + cmd = "peer %s log-change" % peer_addr + else: + cmd = "undo peer %s log-change" % peer_addr + cmds.append(cmd) + + pswd_type = module.params['pswd_type'] + if pswd_type: + conf_str += "%s" % pswd_type + + pswd_cipher_text = module.params['pswd_cipher_text'] + if pswd_cipher_text: + conf_str += "%s" % pswd_cipher_text + + if pswd_type == "cipher": + cmd = "peer %s password cipher %s" % ( + peer_addr, pswd_cipher_text) + elif pswd_type == "simple": + cmd = "peer %s password simple %s" % ( + peer_addr, pswd_cipher_text) + cmds.append(cmd) + + keep_alive_time = module.params['keep_alive_time'] + if keep_alive_time: + conf_str += "%s" % keep_alive_time + + cmd = "peer %s timer keepalive %s" % (peer_addr, keep_alive_time) + cmds.append(cmd) + + hold_time = module.params['hold_time'] + if hold_time: + conf_str += "%s" % hold_time + + cmd = "peer %s timer hold %s" % (peer_addr, hold_time) + cmds.append(cmd) + + min_hold_time = module.params['min_hold_time'] + if min_hold_time: + conf_str += "%s" % min_hold_time + + cmd = "peer %s timer min-holdtime %s" % (peer_addr, min_hold_time) + cmds.append(cmd) + + key_chain_name = module.params['key_chain_name'] + if key_chain_name: + conf_str += "%s" % key_chain_name + + cmd = "peer %s keychain %s" % (peer_addr, key_chain_name) + cmds.append(cmd) + + conn_retry_time = module.params['conn_retry_time'] + if conn_retry_time: + conf_str += "%s" % conn_retry_time + + cmd = "peer %s timer connect-retry %s" % ( + peer_addr, conn_retry_time) + cmds.append(cmd) + + tcp_mss = module.params['tcp_MSS'] + if tcp_mss: + conf_str += "%s" % tcp_mss + + cmd = "peer %s tcp-mss %s" % (peer_addr, tcp_mss) + cmds.append(cmd) + + mpls_local_ifnet_disable = module.params['mpls_local_ifnet_disable'] + if mpls_local_ifnet_disable != 'no_use': + conf_str += "%s" % mpls_local_ifnet_disable + + prepend_global_as = module.params['prepend_global_as'] + if prepend_global_as != 'no_use': + conf_str += "%s" % prepend_global_as + + if prepend_global_as == "true": + cmd = "peer %s public-as-only" % peer_addr + else: + cmd = "undo peer %s public-as-only" % peer_addr + cmds.append(cmd) + + prepend_fake_as = module.params['prepend_fake_as'] + if prepend_fake_as != 'no_use': + conf_str += "%s" % prepend_fake_as + + conf_str += CE_MERGE_BGP_PEER_TAIL + + recv_xml = self.netconf_set_config(module=module, conf_str=conf_str) + + if "" not in recv_xml: + module.fail_json(msg='Error: Merge bgp peer other failed.') + + return cmds + + def merge_peer_bfd(self, **kwargs): + """ merge_peer_bfd """ + + module = kwargs["module"] + vrf_name = module.params['vrf_name'] + peer_addr = module.params['peer_addr'] + + conf_str = CE_MERGE_PEER_BFD_HEADER % (vrf_name, peer_addr) + + cmds = [] + + is_bfd_block = module.params['is_bfd_block'] + if is_bfd_block != 'no_use': + conf_str += "%s" % is_bfd_block + + if is_bfd_block == "true": + cmd = "peer %s bfd block" % peer_addr + else: + cmd = "undo peer %s bfd block" % peer_addr + cmds.append(cmd) + + multiplier = module.params['multiplier'] + if multiplier: + conf_str += "%s" % multiplier + + cmd = "peer %s bfd detect-multiplier %s" % (peer_addr, multiplier) + cmds.append(cmd) + + is_bfd_enable = module.params['is_bfd_enable'] + if is_bfd_enable != 'no_use': + conf_str += "%s" % is_bfd_enable + + if is_bfd_enable == "true": + cmd = "peer %s bfd enable" % peer_addr + else: + cmd = "undo peer %s bfd enable" % peer_addr + cmds.append(cmd) + + rx_interval = module.params['rx_interval'] + if rx_interval: + conf_str += "%s" % rx_interval + + cmd = "peer %s bfd min-rx-interval %s" % (peer_addr, rx_interval) + cmds.append(cmd) + + tx_interval = module.params['tx_interval'] + if tx_interval: + conf_str += "%s" % tx_interval + + cmd = "peer %s bfd min-tx-interval %s" % (peer_addr, tx_interval) + cmds.append(cmd) + + is_single_hop = module.params['is_single_hop'] + if is_single_hop != 'no_use': + conf_str += "%s" % is_single_hop + + if is_single_hop == "true": + cmd = "peer %s bfd enable single-hop-prefer" % peer_addr + else: + cmd = "undo peer %s bfd enable single-hop-prefer" % peer_addr + cmds.append(cmd) + + conf_str += CE_MERGE_PEER_BFD_TAIL + + recv_xml = self.netconf_set_config(module=module, conf_str=conf_str) + + if "" not in recv_xml: + module.fail_json(msg='Error: Merge peer bfd failed.') + + return cmds + + def delete_peer_bfd(self, **kwargs): + """ delete_peer_bfd """ + + module = kwargs["module"] + vrf_name = module.params['vrf_name'] + peer_addr = module.params['peer_addr'] + + conf_str = CE_DELETE_PEER_BFD_HEADER % (vrf_name, peer_addr) + + cmds = [] + + is_bfd_block = module.params['is_bfd_block'] + if is_bfd_block != 'no_use': + conf_str += "%s" % is_bfd_block + + cmd = "undo peer %s bfd block" % peer_addr + cmds.append(cmd) + + multiplier = module.params['multiplier'] + if multiplier: + conf_str += "%s" % multiplier + + cmd = "undo peer %s bfd detect-multiplier %s" % ( + peer_addr, multiplier) + cmds.append(cmd) + + is_bfd_enable = module.params['is_bfd_enable'] + if is_bfd_enable != 'no_use': + conf_str += "%s" % is_bfd_enable + + cmd = "undo peer %s bfd enable" % peer_addr + cmds.append(cmd) + + rx_interval = module.params['rx_interval'] + if rx_interval: + conf_str += "%s" % rx_interval + + cmd = "undo peer %s bfd min-rx-interval %s" % ( + peer_addr, rx_interval) + cmds.append(cmd) + + tx_interval = module.params['tx_interval'] + if tx_interval: + conf_str += "%s" % tx_interval + + cmd = "undo peer %s bfd min-tx-interval %s" % ( + peer_addr, tx_interval) + cmds.append(cmd) + + is_single_hop = module.params['is_single_hop'] + if is_single_hop != 'no_use': + conf_str += "%s" % is_single_hop + + cmd = "undo peer %s bfd enable single-hop-prefer" % peer_addr + cmds.append(cmd) + + conf_str += CE_DELETE_PEER_BFD_TAIL + + recv_xml = self.netconf_set_config(module=module, conf_str=conf_str) + + if "" not in recv_xml: + module.fail_json(msg='Error: Delete peer bfd failed.') + + return cmds + + +def main(): + """ main """ + + argument_spec = dict( + state=dict(choices=['present', 'absent'], default='present'), + vrf_name=dict(type='str', required=True), + peer_addr=dict(type='str', required=True), + remote_as=dict(type='str', required=True), + description=dict(type='str'), + fake_as=dict(type='str'), + dual_as=dict(type='str', default='no_use', choices=['no_use', 'true', 'false']), + conventional=dict(type='str', default='no_use', choices=['no_use', 'true', 'false']), + route_refresh=dict(type='str', default='no_use', choices=['no_use', 'true', 'false']), + four_byte_as=dict(type='str', default='no_use', choices=['no_use', 'true', 'false']), + is_ignore=dict(type='str', default='no_use', choices=['no_use', 'true', 'false']), + local_if_name=dict(type='str'), + ebgp_max_hop=dict(type='str'), + valid_ttl_hops=dict(type='str'), + connect_mode=dict(choices=['listenOnly', 'connectOnly', 'null']), + is_log_change=dict(type='str', default='no_use', choices=['no_use', 'true', 'false']), + pswd_type=dict(choices=['null', 'cipher', 'simple']), + pswd_cipher_text=dict(type='str', no_log=True), + keep_alive_time=dict(type='str'), + hold_time=dict(type='str'), + min_hold_time=dict(type='str'), + key_chain_name=dict(type='str'), + conn_retry_time=dict(type='str'), + tcp_MSS=dict(type='str'), + mpls_local_ifnet_disable=dict(type='str', default='no_use', choices=['no_use', 'true', 'false']), + prepend_global_as=dict(type='str', default='no_use', choices=['no_use', 'true', 'false']), + prepend_fake_as=dict(type='str', default='no_use', choices=['no_use', 'true', 'false']), + is_bfd_block=dict(type='str', default='no_use', choices=['no_use', 'true', 'false']), + multiplier=dict(type='str'), + is_bfd_enable=dict(type='str', default='no_use', choices=['no_use', 'true', 'false']), + rx_interval=dict(type='str'), + tx_interval=dict(type='str'), + is_single_hop=dict(type='str', default='no_use', choices=['no_use', 'true', 'false'])) + + argument_spec.update(ce_argument_spec) + module = AnsibleModule(argument_spec=argument_spec, supports_check_mode=True) + + changed = False + proposed = dict() + existing = dict() + end_state = dict() + updates = [] + + state = module.params['state'] + vrf_name = module.params['vrf_name'] + peer_addr = module.params['peer_addr'] + remote_as = module.params['remote_as'] + description = module.params['description'] + fake_as = module.params['fake_as'] + dual_as = module.params['dual_as'] + conventional = module.params['conventional'] + route_refresh = module.params['route_refresh'] + four_byte_as = module.params['four_byte_as'] + is_ignore = module.params['is_ignore'] + local_if_name = module.params['local_if_name'] + ebgp_max_hop = module.params['ebgp_max_hop'] + valid_ttl_hops = module.params['valid_ttl_hops'] + connect_mode = module.params['connect_mode'] + is_log_change = module.params['is_log_change'] + pswd_type = module.params['pswd_type'] + pswd_cipher_text = module.params['pswd_cipher_text'] + keep_alive_time = module.params['keep_alive_time'] + hold_time = module.params['hold_time'] + min_hold_time = module.params['min_hold_time'] + key_chain_name = module.params['key_chain_name'] + conn_retry_time = module.params['conn_retry_time'] + tcp_mss = module.params['tcp_MSS'] + mpls_local_ifnet_disable = module.params['mpls_local_ifnet_disable'] + prepend_global_as = module.params['prepend_global_as'] + prepend_fake_as = module.params['prepend_fake_as'] + is_bfd_block = module.params['is_bfd_block'] + multiplier = module.params['multiplier'] + is_bfd_enable = module.params['is_bfd_enable'] + rx_interval = module.params['rx_interval'] + tx_interval = module.params['tx_interval'] + is_single_hop = module.params['is_single_hop'] + + ce_bgp_peer_obj = BgpNeighbor() + + # get proposed + proposed["state"] = state + if vrf_name: + proposed["vrf_name"] = vrf_name + if peer_addr: + proposed["peer_addr"] = peer_addr + if remote_as: + proposed["remote_as"] = remote_as + if description: + proposed["description"] = description + if fake_as: + proposed["fake_as"] = fake_as + if dual_as != 'no_use': + proposed["dual_as"] = dual_as + if conventional != 'no_use': + proposed["conventional"] = conventional + if route_refresh != 'no_use': + proposed["route_refresh"] = route_refresh + if four_byte_as != 'no_use': + proposed["four_byte_as"] = four_byte_as + if is_ignore != 'no_use': + proposed["is_ignore"] = is_ignore + if local_if_name: + proposed["local_if_name"] = local_if_name + if ebgp_max_hop: + proposed["ebgp_max_hop"] = ebgp_max_hop + if valid_ttl_hops: + proposed["valid_ttl_hops"] = valid_ttl_hops + if connect_mode: + proposed["connect_mode"] = connect_mode + if is_log_change != 'no_use': + proposed["is_log_change"] = is_log_change + if pswd_type: + proposed["pswd_type"] = pswd_type + if pswd_cipher_text: + proposed["pswd_cipher_text"] = pswd_cipher_text + if keep_alive_time: + proposed["keep_alive_time"] = keep_alive_time + if hold_time: + proposed["hold_time"] = hold_time + if min_hold_time: + proposed["min_hold_time"] = min_hold_time + if key_chain_name: + proposed["key_chain_name"] = key_chain_name + if conn_retry_time: + proposed["conn_retry_time"] = conn_retry_time + if tcp_mss: + proposed["tcp_MSS"] = tcp_mss + if mpls_local_ifnet_disable != 'no_use': + proposed["mpls_local_ifnet_disable"] = mpls_local_ifnet_disable + if prepend_global_as != 'no_use': + proposed["prepend_global_as"] = prepend_global_as + if prepend_fake_as != 'no_use': + proposed["prepend_fake_as"] = prepend_fake_as + if is_bfd_block != 'no_use': + proposed["is_bfd_block"] = is_bfd_block + if multiplier: + proposed["multiplier"] = multiplier + if is_bfd_enable != 'no_use': + proposed["is_bfd_enable"] = is_bfd_enable + if rx_interval: + proposed["rx_interval"] = rx_interval + if tx_interval: + proposed["tx_interval"] = tx_interval + if is_single_hop != 'no_use': + proposed["is_single_hop"] = is_single_hop + + if not ce_bgp_peer_obj: + module.fail_json(msg='Error: Init module failed.') + + need_bgp_peer_enable = ce_bgp_peer_obj.check_bgp_peer_args(module=module) + need_bgp_peer_other_rst = ce_bgp_peer_obj.check_bgp_peer_other_args( + module=module) + need_peer_bfd_merge_rst = ce_bgp_peer_obj.check_peer_bfd_merge_args( + module=module) + need_peer_bfd_del_rst = ce_bgp_peer_obj.check_peer_bfd_delete_args( + module=module) + + # bgp peer config + if need_bgp_peer_enable["need_cfg"]: + + if state == "present": + + if remote_as: + + bgp_peer_exist = ce_bgp_peer_obj.get_bgp_peer(module=module) + existing["bgp peer"] = bgp_peer_exist + + bgp_peer_new = (peer_addr, remote_as) + + if len(bgp_peer_exist) == 0: + cmd = ce_bgp_peer_obj.create_bgp_peer(module=module) + changed = True + for item in cmd: + updates.append(item) + + elif bgp_peer_new in bgp_peer_exist: + pass + + else: + cmd = ce_bgp_peer_obj.merge_bgp_peer(module=module) + changed = True + for item in cmd: + updates.append(item) + + bgp_peer_end = ce_bgp_peer_obj.get_bgp_peer(module=module) + end_state["bgp peer"] = bgp_peer_end + + else: + + bgp_peer_exist = ce_bgp_peer_obj.get_bgp_del_peer(module=module) + existing["bgp peer"] = bgp_peer_exist + + bgp_peer_new = (peer_addr) + + if len(bgp_peer_exist) == 0: + pass + + elif bgp_peer_new in bgp_peer_exist: + cmd = ce_bgp_peer_obj.delete_bgp_peer(module=module) + changed = True + for item in cmd: + updates.append(item) + + bgp_peer_end = ce_bgp_peer_obj.get_bgp_del_peer(module=module) + end_state["bgp peer"] = bgp_peer_end + + # bgp peer other args + exist_tmp = dict() + for item in need_bgp_peer_other_rst: + if item != "need_cfg": + exist_tmp[item] = need_bgp_peer_other_rst[item] + if exist_tmp: + existing["bgp peer other"] = exist_tmp + + if need_bgp_peer_other_rst["need_cfg"]: + + if state == "present": + cmd = ce_bgp_peer_obj.merge_bgp_peer_other(module=module) + changed = True + for item in cmd: + updates.append(item) + + need_bgp_peer_other_rst = ce_bgp_peer_obj.check_bgp_peer_other_args( + module=module) + end_tmp = dict() + for item in need_bgp_peer_other_rst: + if item != "need_cfg": + end_tmp[item] = need_bgp_peer_other_rst[item] + if end_tmp: + end_state["bgp peer other"] = end_tmp + + # peer bfd args + if state == "present": + exist_tmp = dict() + for item in need_peer_bfd_merge_rst: + if item != "need_cfg": + exist_tmp[item] = need_peer_bfd_merge_rst[item] + if exist_tmp: + existing["peer bfd"] = exist_tmp + + if need_peer_bfd_merge_rst["need_cfg"]: + cmd = ce_bgp_peer_obj.merge_peer_bfd(module=module) + changed = True + for item in cmd: + updates.append(item) + + need_peer_bfd_merge_rst = ce_bgp_peer_obj.check_peer_bfd_merge_args( + module=module) + end_tmp = dict() + for item in need_peer_bfd_merge_rst: + if item != "need_cfg": + end_tmp[item] = need_peer_bfd_merge_rst[item] + if end_tmp: + end_state["peer bfd"] = end_tmp + else: + exist_tmp = dict() + for item in need_peer_bfd_del_rst: + if item != "need_cfg": + exist_tmp[item] = need_peer_bfd_del_rst[item] + if exist_tmp: + existing["peer bfd"] = exist_tmp + + # has already delete with bgp peer + + need_peer_bfd_del_rst = ce_bgp_peer_obj.check_peer_bfd_delete_args( + module=module) + end_tmp = dict() + for item in need_peer_bfd_del_rst: + if item != "need_cfg": + end_tmp[item] = need_peer_bfd_del_rst[item] + if end_tmp: + end_state["peer bfd"] = end_tmp + + results = dict() + results['proposed'] = proposed + results['existing'] = existing + results['changed'] = changed + results['end_state'] = end_state + results['updates'] = updates + + module.exit_json(**results) + + +if __name__ == '__main__': + main()