1# 2# (c) 2019, Ansible by Red Hat, inc 3# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt) 4# 5from __future__ import absolute_import, division, print_function 6 7__metaclass__ = type 8import re 9 10from ansible.module_utils.six import iteritems 11from ansible_collections.ansible.netcommon.plugins.module_utils.network.common.utils import ( 12 to_list, 13) 14from ansible_collections.cisco.ios.plugins.module_utils.network.ios.providers.providers import ( 15 CliProvider, 16) 17 18 19class Neighbors(CliProvider): 20 def render(self, config=None, nbr_list=None): 21 commands = list() 22 safe_list = list() 23 if not nbr_list: 24 nbr_list = self.get_value("config.neighbors") 25 26 for item in nbr_list: 27 neighbor_commands = list() 28 context = "neighbor %s" % item["neighbor"] 29 cmd = "%s remote-as %s" % (context, item["remote_as"]) 30 31 if not config or cmd not in config: 32 neighbor_commands.append(cmd) 33 34 for key, value in iteritems(item): 35 if value is not None: 36 meth = getattr(self, "_render_%s" % key, None) 37 if meth: 38 resp = meth(item, config) 39 if resp: 40 neighbor_commands.extend(to_list(resp)) 41 42 commands.extend(neighbor_commands) 43 safe_list.append(context) 44 45 if self.params["operation"] == "replace": 46 if config and safe_list: 47 commands.extend(self._negate_config(config, safe_list)) 48 49 return commands 50 51 def _negate_config(self, config, safe_list=None): 52 commands = list() 53 matches = re.findall(r"(neighbor \S+)", config, re.M) 54 for item in set(matches).difference(safe_list): 55 commands.append("no %s" % item) 56 return commands 57 58 def _render_local_as(self, item, config=None): 59 cmd = "neighbor %s local-as %s" % (item["neighbor"], item["local_as"]) 60 if not config or cmd not in config: 61 return cmd 62 63 def _render_port(self, item, config=None): 64 cmd = "neighbor %s port %s" % (item["neighbor"], item["port"]) 65 if not config or cmd not in config: 66 return cmd 67 68 def _render_description(self, item, config=None): 69 cmd = "neighbor %s description %s" % ( 70 item["neighbor"], 71 item["description"], 72 ) 73 if not config or cmd not in config: 74 return cmd 75 76 def _render_enabled(self, item, config=None): 77 cmd = "neighbor %s shutdown" % item["neighbor"] 78 if item["enabled"] is True: 79 if not config or cmd in config: 80 cmd = "no %s" % cmd 81 return cmd 82 elif not config or cmd not in config: 83 return cmd 84 85 def _render_update_source(self, item, config=None): 86 cmd = "neighbor %s update-source %s" % ( 87 item["neighbor"], 88 item["update_source"], 89 ) 90 if not config or cmd not in config: 91 return cmd 92 93 def _render_password(self, item, config=None): 94 cmd = "neighbor %s password %s" % (item["neighbor"], item["password"]) 95 if not config or cmd not in config: 96 return cmd 97 98 def _render_ebgp_multihop(self, item, config=None): 99 cmd = "neighbor %s ebgp-multihop %s" % ( 100 item["neighbor"], 101 item["ebgp_multihop"], 102 ) 103 if not config or cmd not in config: 104 return cmd 105 106 def _render_peer_group(self, item, config=None): 107 cmd = "neighbor %s peer-group %s" % ( 108 item["neighbor"], 109 item["peer_group"], 110 ) 111 if not config or cmd not in config: 112 return cmd 113 114 def _render_timers(self, item, config): 115 """generate bgp timer related configuration 116 """ 117 keepalive = item["timers"]["keepalive"] 118 holdtime = item["timers"]["holdtime"] 119 min_neighbor_holdtime = item["timers"]["min_neighbor_holdtime"] 120 neighbor = item["neighbor"] 121 122 if keepalive and holdtime: 123 cmd = "neighbor %s timers %s %s" % (neighbor, keepalive, holdtime) 124 if min_neighbor_holdtime: 125 cmd += " %s" % min_neighbor_holdtime 126 if not config or cmd not in config: 127 return cmd 128 129 130class AFNeighbors(CliProvider): 131 def render(self, config=None, nbr_list=None): 132 commands = list() 133 if not nbr_list: 134 return 135 136 for item in nbr_list: 137 neighbor_commands = list() 138 for key, value in iteritems(item): 139 if value is not None: 140 meth = getattr(self, "_render_%s" % key, None) 141 if meth: 142 resp = meth(item, config) 143 if resp: 144 neighbor_commands.extend(to_list(resp)) 145 146 commands.extend(neighbor_commands) 147 148 return commands 149 150 def _render_advertisement_interval(self, item, config=None): 151 cmd = "neighbor %s advertisement-interval %s" % ( 152 item["neighbor"], 153 item["advertisement_interval"], 154 ) 155 if not config or cmd not in config: 156 return cmd 157 158 def _render_route_reflector_client(self, item, config=None): 159 cmd = "neighbor %s route-reflector-client" % item["neighbor"] 160 if item["route_reflector_client"] is False: 161 if not config or cmd in config: 162 cmd = "no %s" % cmd 163 return cmd 164 elif not config or cmd not in config: 165 return cmd 166 167 def _render_route_server_client(self, item, config=None): 168 cmd = "neighbor %s route-server-client" % item["neighbor"] 169 if item["route_server_client"] is False: 170 if not config or cmd in config: 171 cmd = "no %s" % cmd 172 return cmd 173 elif not config or cmd not in config: 174 return cmd 175 176 def _render_remove_private_as(self, item, config=None): 177 cmd = "neighbor %s remove-private-as" % item["neighbor"] 178 if item["remove_private_as"] is False: 179 if not config or cmd in config: 180 cmd = "no %s" % cmd 181 return cmd 182 elif not config or cmd not in config: 183 return cmd 184 185 def _render_next_hop_self(self, item, config=None): 186 cmd = "neighbor %s next-hop-self" % item["neighbor"] 187 if item["next_hop_self"] is False: 188 if not config or cmd in config: 189 cmd = "no %s" % cmd 190 return cmd 191 elif not config or cmd not in config: 192 return cmd 193 194 def _render_activate(self, item, config=None): 195 cmd = "neighbor %s activate" % item["neighbor"] 196 if item["activate"] is False: 197 if not config or cmd in config: 198 cmd = "no %s" % cmd 199 return cmd 200 elif not config or cmd not in config: 201 return cmd 202 203 def _render_maximum_prefix(self, item, config=None): 204 cmd = "neighbor %s maximum-prefix %s" % ( 205 item["neighbor"], 206 item["maximum_prefix"], 207 ) 208 if not config or cmd not in config: 209 return cmd 210 211 def _render_prefix_list_in(self, item, config=None): 212 cmd = "neighbor %s prefix-list %s in" % ( 213 item["neighbor"], 214 item["prefix_list_in"], 215 ) 216 if not config or cmd not in config: 217 return cmd 218 219 def _render_prefix_list_out(self, item, config=None): 220 cmd = "neighbor %s prefix-list %s out" % ( 221 item["neighbor"], 222 item["prefix_list_out"], 223 ) 224 if not config or cmd not in config: 225 return cmd 226