]> git.proxmox.com Git - mirror_frr.git/blame - tests/topotests/bgp_vrf_dynamic_route_leak_topo3/test_bgp_vrf_dynamic_route_leak_topo3.py
*: auto-convert to SPDX License IDs
[mirror_frr.git] / tests / topotests / bgp_vrf_dynamic_route_leak_topo3 / test_bgp_vrf_dynamic_route_leak_topo3.py
CommitLineData
133fd9ed 1#!/usr/bin/env python
acddc0ed 2# SPDX-License-Identifier: ISC
133fd9ed
KK
3
4#
5# Copyright (c) 2021 by VMware, Inc. ("VMware")
6# Used Copyright (c) 2018 by Network Device Education Foundation,
7# Inc. ("NetDEF") in this file.
8#
133fd9ed
KK
9
10"""
11Following tests are covered to test BGP Multi-VRF Dynamic Route Leaking:
121. Verify that with multiple tenant VRFs, dynamically imported routes are
13 further advertised to eBGP peers.
142. Verify the route-map operations along with dynamic import command
153. Verify that deleting static routes from originating VRF also deletes
16 routes from other VRFs and peers.
174. Verify that deleting and adding "import" command multiple times shows
18 consistent results.
19"""
20
21import os
22import sys
23import time
24import pytest
25import platform
26from time import sleep
27
28# Save the Current Working Directory to find configuration files.
29CWD = os.path.dirname(os.path.realpath(__file__))
30sys.path.append(os.path.join(CWD, "../"))
31sys.path.append(os.path.join(CWD, "../lib/"))
32
33# Required to instantiate the topology builder class.
34
35# pylint: disable=C0413
36# Import topogen and topotest helpers
37from lib.topogen import Topogen, get_topogen
38from lib.topotest import version_cmp
39
40from lib.common_config import (
41 start_topology,
42 write_test_header,
43 check_address_types,
44 write_test_footer,
45 reset_config_on_routers,
46 verify_rib,
47 step,
48 create_route_maps,
49 create_static_routes,
50 create_prefix_lists,
51 create_bgp_community_lists,
52 get_frr_ipv6_linklocal,
53)
54
55from lib.topolog import logger
56from lib.bgp import (
57 verify_bgp_convergence,
58 create_router_bgp,
59 verify_bgp_community,
60 verify_bgp_rib,
61)
62from lib.topojson import build_config_from_json
63
64pytestmark = [pytest.mark.bgpd, pytest.mark.staticd]
65
66# Global variables
67NETWORK1_1 = {"ipv4": "11.11.11.1/32", "ipv6": "11:11::1/128"}
68NETWORK1_2 = {"ipv4": "11.11.11.11/32", "ipv6": "11:11::11/128"}
69NETWORK1_3 = {"ipv4": "10.10.10.1/32", "ipv6": "10:10::1/128"}
70NETWORK1_4 = {"ipv4": "10.10.10.100/32", "ipv6": "10:10::100/128"}
71NETWORK1_5 = {"ipv4": "110.110.110.1/32", "ipv6": "110:110::1/128"}
72NETWORK1_6 = {"ipv4": "110.110.110.100/32", "ipv6": "110:110::100/128"}
73
74NETWORK2_1 = {"ipv4": "22.22.22.2/32", "ipv6": "22:22::2/128"}
75NETWORK2_2 = {"ipv4": "22.22.22.22/32", "ipv6": "22:22::22/128"}
76NETWORK2_3 = {"ipv4": "20.20.20.20/32", "ipv6": "20:20::20/128"}
77NETWORK2_4 = {"ipv4": "20.20.20.200/32", "ipv6": "20:20::200/128"}
78NETWORK2_5 = {"ipv4": "220.220.220.20/32", "ipv6": "220:220::20/128"}
79NETWORK2_6 = {"ipv4": "220.220.220.200/32", "ipv6": "220:220::200/128"}
80
81NETWORK3_1 = {"ipv4": "30.30.30.3/32", "ipv6": "30:30::3/128"}
82NETWORK3_2 = {"ipv4": "30.30.30.30/32", "ipv6": "30:30::30/128"}
83
84PREFIX_LIST = {
85 "ipv4": ["11.11.11.1", "22.22.22.2", "22.22.22.22"],
86 "ipv6": ["11:11::1", "22:22::2", "22:22::22"],
87}
88PREFERRED_NEXT_HOP = "global"
89VRF_LIST = ["RED", "BLUE", "GREEN"]
90COMM_VAL_1 = "100:100"
91COMM_VAL_2 = "500:500"
92COMM_VAL_3 = "600:600"
93
94
95def setup_module(mod):
96 """
97 Sets up the pytest environment
98
99 * `mod`: module name
100 """
101
102 testsuite_run_time = time.asctime(time.localtime(time.time()))
103 logger.info("Testsuite start time: {}".format(testsuite_run_time))
104 logger.info("=" * 40)
105
106 logger.info("Running setup_module to create topology")
107
108 # This function initiates the topology build with Topogen...
109 json_file = "{}/bgp_vrf_dynamic_route_leak_topo3.json".format(CWD)
110 tgen = Topogen(json_file, mod.__name__)
111 global topo
112 topo = tgen.json_topo
113 # ... and here it calls Mininet initialization functions.
114
115 # Starting topology, create tmp files which are loaded to routers
d60a3f0e 116 # to start daemons and then start routers
133fd9ed
KK
117 start_topology(tgen)
118
119 # Run these tests for kernel version 4.19 or above
120 if version_cmp(platform.release(), "4.19") < 0:
121 error_msg = (
122 "BGP vrf dynamic route leak tests will not run "
123 '(have kernel "{}", but it requires >= 4.19)'.format(platform.release())
124 )
125 pytest.skip(error_msg)
126
127 # Creating configuration from JSON
128 build_config_from_json(tgen, topo)
129
130 global BGP_CONVERGENCE
131 global ADDR_TYPES
132 ADDR_TYPES = check_address_types()
133
134 BGP_CONVERGENCE = verify_bgp_convergence(tgen, topo)
135 assert BGP_CONVERGENCE is True, "setup_module : Failed \n Error: {}".format(
136 BGP_CONVERGENCE
137 )
138
139 logger.info("Running setup_module() done")
140
141
142def teardown_module():
143 """Teardown the pytest environment"""
144
145 logger.info("Running teardown_module to delete topology")
146
147 tgen = get_topogen()
148
149 # Stop toplogy and Remove tmp files
150 tgen.stop_topology()
151
152 logger.info(
153 "Testsuite end time: {}".format(time.asctime(time.localtime(time.time())))
154 )
155 logger.info("=" * 40)
156
157
158#####################################################
159#
160# Testcases
161#
162#####################################################
163
164
165def test_dynamic_import_routes_advertised_to_ebgp_peers_p0(request):
166 """
167 Verify that with multiple tenant VRFs, dynamically imported routes are
168 further advertised to eBGP peers.
169 """
170
171 tgen = get_topogen()
172 tc_name = request.node.name
173 write_test_header(tc_name)
174 reset_config_on_routers(tgen)
175 if tgen.routers_have_failure():
176 pytest.skip(tgen.errors)
177
178 step(
179 "Configure static routes on R2 and R3 and redistribute in BGP for "
180 "BLUE and RED vrf instances"
181 )
182 for dut, network in zip(
183 ["r2", "r3"], [[NETWORK1_1, NETWORK1_2], [NETWORK2_1, NETWORK2_2]]
184 ):
185 for vrf_name, network_vrf in zip(["RED", "BLUE"], network):
186 step("Configure static route for VRF : {} on {}".format(vrf_name, dut))
187 for addr_type in ADDR_TYPES:
188 static_routes = {
189 dut: {
190 "static_routes": [
191 {
192 "network": [network_vrf[addr_type]],
193 "next_hop": "blackhole",
194 "vrf": vrf_name,
195 }
196 ]
197 }
198 }
199
200 result = create_static_routes(tgen, static_routes)
201 assert result is True, "Testcase {} :Failed \n Error: {}".format(
202 tc_name, result
203 )
204
205 for dut, as_num in zip(["r2", "r3"], ["2", "3"]):
206 for vrf_name in ["RED", "BLUE"]:
207 step("Redistribute static route on BGP VRF : {}".format(vrf_name))
208 temp = {}
209 for addr_type in ADDR_TYPES:
210 temp.update(
211 {
212 addr_type: {
213 "unicast": {"redistribute": [{"redist_type": "static"}]}
214 }
215 }
216 )
217
218 redist_dict = {
219 dut: {
220 "bgp": [
221 {"vrf": vrf_name, "local_as": as_num, "address_family": temp}
222 ]
223 }
224 }
225
226 result = create_router_bgp(tgen, topo, redist_dict)
227 assert result is True, "Testcase {} :Failed \n Error: {}".format(
228 tc_name, result
229 )
230
231 step(
232 "Verify that R2 and R3 has installed redistributed routes in BLUE "
233 "and RED vrfs"
234 )
235 for dut, network in zip(
236 ["r2", "r3"], [[NETWORK2_1, NETWORK2_2], [NETWORK1_1, NETWORK1_2]]
237 ):
238 for vrf_name, network_vrf in zip(["RED", "BLUE"], network):
239 for addr_type in ADDR_TYPES:
240 static_routes = {
241 dut: {
242 "static_routes": [
243 {
244 "network": [network_vrf[addr_type]],
245 "next_hop": "blackhole",
246 "vrf": vrf_name,
247 }
248 ]
249 }
250 }
251 result = verify_bgp_rib(tgen, addr_type, dut, static_routes)
252 assert result is True, "Testcase {} : Failed \n Error {}".format(
253 tc_name, result
254 )
255
256 result = verify_rib(tgen, addr_type, dut, static_routes)
257 assert result is True, "Testcase {} : Failed \n Error {}".format(
258 tc_name, result
259 )
260
261 step(
262 "Import BLUE vrf's route in tenant vrf RED on R2 and then import "
263 "vrf RED's routes into BLUE vrf on R3"
264 )
265
266 for dut, as_num, vrf_name, vrf_import in zip(
267 ["r2", "r3"], ["2", "3"], ["RED", "BLUE"], ["BLUE", "RED"]
268 ):
269 step("Import vrf {} int vrf {}, on router {}".format(vrf_import, vrf_name, dut))
270 temp = {}
271 for addr_type in ADDR_TYPES:
272 temp.update({addr_type: {"unicast": {"import": {"vrf": vrf_import}}}})
273
274 import_dict = {
275 dut: {
276 "bgp": [{"vrf": vrf_name, "local_as": as_num, "address_family": temp}]
277 }
278 }
279
280 result = create_router_bgp(tgen, topo, import_dict)
281 assert result is True, "Testcase {} :Failed \n Error: {}".format(
282 tc_name, result
283 )
284
285 step(
286 "Verify that R2's vrf RED and R3's vrf BLUE has installed 4 set of "
287 "prefixes. Routes imported from BLUE vrf (originated R2's & received "
288 "from R3). Vrf RED's local routes (originated by R2's & received "
289 "from R3)"
290 )
291 step(
292 "Verify that R2 and R3 has installed redistributed routes in BLUE "
293 "and RED vrfs"
294 )
295
296 for dut, vrf_name in zip(["r2", "r3"], ["RED", "BLUE"]):
297 for addr_type in ADDR_TYPES:
298 static_routes = {
299 dut: {
300 "static_routes": [
301 {
302 "network": [
303 NETWORK1_1[addr_type],
304 NETWORK1_2[addr_type],
305 NETWORK2_1[addr_type],
306 NETWORK2_2[addr_type],
307 ],
308 "next_hop": "blackhole",
309 "vrf": vrf_name,
310 }
311 ]
312 }
313 }
314 result = verify_bgp_rib(tgen, addr_type, dut, static_routes)
315 assert result is True, "Testcase {} : Failed \n Error {}".format(
316 tc_name, result
317 )
318
319 result = verify_rib(tgen, addr_type, dut, static_routes)
320 assert result is True, "Testcase {} : Failed \n Error {}".format(
321 tc_name, result
322 )
323
324 step(
325 "Additionally, R2 receives R3's BLUE vrf's prefixes and then import "
326 "into vrf RED. These imported routes are advertised back to "
327 "(originator)R3 but now in vrf RED, however R3 doesn't install these "
328 "in vrf RED. Denied due to own AS"
329 )
330 for addr_type in ADDR_TYPES:
331 static_routes = {
332 "r3": {
333 "static_routes": [
334 {
335 "network": [
336 NETWORK1_1[addr_type],
337 NETWORK1_2[addr_type],
338 NETWORK2_1[addr_type],
339 NETWORK2_2[addr_type],
340 ],
341 "next_hop": "blackhole",
342 "vrf": "RED",
343 }
344 ]
345 }
346 }
347 result = verify_bgp_rib(tgen, addr_type, "r3", static_routes, expected=False)
348 assert (
349 result is not True
350 ), "Testcase {} : Failed \nError {}\n" "Routes {} still in BGP table".format(
351 tc_name, result, static_routes["r3"]["static_routes"][0]["network"]
352 )
353
354 result = verify_rib(tgen, addr_type, "r3", static_routes, expected=False)
355 assert result is not True, "Testcase {} : Failed \n Error {}".format(
356 tc_name, result
357 )
358
359 step("Remove import vrf BLUE from vrf RED's instance on R2.")
360 temp = {}
361 for addr_type in ADDR_TYPES:
362 temp.update(
363 {addr_type: {"unicast": {"import": {"vrf": "BLUE", "delete": True}}}}
364 )
365
366 import_dict = {
367 "r2": {"bgp": [{"vrf": "RED", "local_as": 2, "address_family": temp}]}
368 }
369
370 result = create_router_bgp(tgen, topo, import_dict)
371 assert result is True, "Testcase {} :Failed \n Error: {}".format(tc_name, result)
372 step(
373 "Verify on R3 that, there is no change in FIB of vrf BLUE and R2's "
374 "BLUE vrf originated routes are removed from vrf RED on R3."
375 )
376 for vrf_name in ["RED", "BLUE"]:
377 for addr_type in ADDR_TYPES:
378 if vrf_name == "RED":
379 network_vrf = [NETWORK1_1[addr_type], NETWORK2_1[addr_type]]
380 elif vrf_name == "BLUE":
381 network_vrf = [
382 NETWORK1_1[addr_type],
383 NETWORK1_2[addr_type],
384 NETWORK2_1[addr_type],
385 NETWORK2_2[addr_type],
386 ]
387 static_routes = {
388 "r3": {
389 "static_routes": [
390 {
391 "network": network_vrf,
392 "next_hop": "blackhole",
393 "vrf": vrf_name,
394 }
395 ]
396 }
397 }
398 result = verify_bgp_rib(tgen, addr_type, "r3", static_routes)
399 assert result is True, "Testcase {} : Failed \n Error {}".format(
400 tc_name, result
401 )
402
403 result = verify_rib(tgen, addr_type, "r3", static_routes)
404 assert result is True, "Testcase {} : Failed \n Error {}".format(
405 tc_name, result
406 )
407
408 step("Remove import vrf BLUE from vrf RED's instance on R2.")
409 temp = {}
410 for addr_type in ADDR_TYPES:
411 temp.update({addr_type: {"unicast": {"import": {"vrf": "BLUE"}}}})
412
413 import_dict = {
414 "r2": {"bgp": [{"vrf": "RED", "local_as": 2, "address_family": temp}]}
415 }
416
417 result = create_router_bgp(tgen, topo, import_dict)
418 assert result is True, "Testcase {} :Failed \n Error: {}".format(tc_name, result)
419
420 step(
421 "All the routes described in earlier step should be added, once "
422 "import command on R2 is re-added."
423 )
424 for dut, vrf_name in zip(["r2", "r3"], ["RED", "BLUE"]):
425 for addr_type in ADDR_TYPES:
426 static_routes = {
427 dut: {
428 "static_routes": [
429 {
430 "network": [
431 NETWORK1_1[addr_type],
432 NETWORK1_2[addr_type],
433 NETWORK2_1[addr_type],
434 NETWORK2_2[addr_type],
435 ],
436 "next_hop": "blackhole",
437 "vrf": vrf_name,
438 }
439 ]
440 }
441 }
442 result = verify_bgp_rib(tgen, addr_type, dut, static_routes)
443 assert result is True, "Testcase {} : Failed \n Error {}".format(
444 tc_name, result
445 )
446
447 result = verify_rib(tgen, addr_type, dut, static_routes)
448 assert result is True, "Testcase {} : Failed \n Error {}".format(
449 tc_name, result
450 )
451
452 step("Remove import vrf RED from BLUE vrf on R3")
453 temp = {}
454 for addr_type in ADDR_TYPES:
455 temp.update(
456 {addr_type: {"unicast": {"import": {"vrf": "RED", "delete": True}}}}
457 )
458
459 import_dict = {
460 "r3": {"bgp": [{"vrf": "BLUE", "local_as": 3, "address_family": temp}]}
461 }
462
463 result = create_router_bgp(tgen, topo, import_dict)
464 assert result is True, "Testcase {} :Failed \n Error: {}".format(tc_name, result)
465
466 step(
467 "Verify on R2 that, there is no change in FIB of vrf RED and R3's "
468 "vrf RED's originated routes are removed from vrf BLUE on R2."
469 )
470 for vrf_name in ["RED", "BLUE"]:
471 for addr_type in ADDR_TYPES:
472 if vrf_name == "BLUE":
473 network_vrf = [NETWORK1_2[addr_type], NETWORK2_2[addr_type]]
474 elif vrf_name == "RED":
475 network_vrf = [
476 NETWORK1_1[addr_type],
477 NETWORK1_2[addr_type],
478 NETWORK2_1[addr_type],
479 NETWORK2_2[addr_type],
480 ]
481 static_routes = {
482 "r2": {
483 "static_routes": [
484 {
485 "network": network_vrf,
486 "next_hop": "blackhole",
487 "vrf": vrf_name,
488 }
489 ]
490 }
491 }
492 result = verify_bgp_rib(tgen, addr_type, "r2", static_routes)
493 assert result is True, "Testcase {} : Failed \n Error {}".format(
494 tc_name, result
495 )
496
497 result = verify_rib(tgen, addr_type, "r2", static_routes)
498 assert result is True, "Testcase {} : Failed \n Error {}".format(
499 tc_name, result
500 )
501
502 step("Add import vrf RED from BLUE vrf on R3")
503 temp = {}
504 for addr_type in ADDR_TYPES:
505 temp.update({addr_type: {"unicast": {"import": {"vrf": "RED"}}}})
506
507 import_dict = {
508 "r3": {"bgp": [{"vrf": "BLUE", "local_as": 3, "address_family": temp}]}
509 }
510
511 result = create_router_bgp(tgen, topo, import_dict)
512 assert result is True, "Testcase {} :Failed \n Error: {}".format(tc_name, result)
513
514 step(
515 "All the routes described in earlier step should be added, once "
516 "import command on R2 is re-added."
517 )
518 for dut, vrf_name in zip(["r2", "r3"], ["RED", "BLUE"]):
519 for addr_type in ADDR_TYPES:
520 static_routes = {
521 dut: {
522 "static_routes": [
523 {
524 "network": [
525 NETWORK1_1[addr_type],
526 NETWORK1_2[addr_type],
527 NETWORK2_1[addr_type],
528 NETWORK2_2[addr_type],
529 ],
530 "next_hop": "blackhole",
531 "vrf": vrf_name,
532 }
533 ]
534 }
535 }
536 result = verify_bgp_rib(tgen, addr_type, dut, static_routes)
537 assert result is True, "Testcase {} : Failed \n Error {}".format(
538 tc_name, result
539 )
540
541 result = verify_rib(tgen, addr_type, dut, static_routes)
542 assert result is True, "Testcase {} : Failed \n Error {}".format(
543 tc_name, result
544 )
545
546 write_test_footer(tc_name)
547
548
549def test_dynamic_imported_matching_prefix_based_on_community_list_p0(request):
550 """
551 Verify the route-map operations along with dynamic import command
552 """
553
554 tgen = get_topogen()
555 tc_name = request.node.name
556 write_test_header(tc_name)
557 reset_config_on_routers(tgen)
558 if tgen.routers_have_failure():
559 pytest.skip(tgen.errors)
560
561 step(
562 "Configure static routes on R3 for vrf RED and redistribute in BGP " "instance"
563 )
564 for vrf_name, networks in zip(
565 ["RED", "BLUE"], [[NETWORK1_1, NETWORK1_2], [NETWORK2_1, NETWORK2_2]]
566 ):
567 for addr_type in ADDR_TYPES:
568 static_routes = {
569 "r3": {
570 "static_routes": [
571 {
572 "network": [networks[0][addr_type], networks[1][addr_type]],
573 "next_hop": "blackhole",
574 "vrf": vrf_name,
575 }
576 ]
577 }
578 }
579
580 result = create_static_routes(tgen, static_routes)
581 assert result is True, "Testcase {} :Failed \n Error: {}".format(
582 tc_name, result
583 )
584
585 step(
586 "Configure route-map to set community attribute for a specific " "prefix on R3"
587 )
588 for addr_type in ADDR_TYPES:
589 input_dict_pf = {
590 "r3": {
591 "prefix_lists": {
592 addr_type: {
593 "pflist_ABC_{}".format(addr_type): [
594 {
595 "seqid": 10,
596 "network": NETWORK1_1[addr_type],
597 "action": "permit",
598 }
599 ]
600 }
601 }
602 }
603 }
604 result = create_prefix_lists(tgen, input_dict_pf)
605 assert result is True, "Testcase {} : Failed \n Error: {}".format(
606 tc_name, result
607 )
608
609 input_dict_cl = {
610 "r3": {
611 "bgp_community_lists": [
612 {
613 "community_type": "expanded",
614 "action": "permit",
615 "name": "COMM",
616 "value": COMM_VAL_1,
617 }
618 ]
619 }
620 }
621 result = create_bgp_community_lists(tgen, input_dict_cl)
622 assert result is True, "Testcase {} : Failed \n Error: {}".format(tc_name, result)
623
624 for addr_type in ADDR_TYPES:
625 input_dict_rm = {
626 "r3": {
627 "route_maps": {
628 "rmap_XYZ_{}".format(addr_type): [
629 {
630 "action": "permit",
631 "match": {
632 addr_type: {
633 "prefix_lists": "pflist_ABC_{}".format(addr_type)
634 }
635 },
636 "set": {"community": {"num": COMM_VAL_1}},
637 }
638 ]
639 }
640 }
641 }
642 result = create_route_maps(tgen, input_dict_rm)
643 assert result is True, "Testcase {} : Failed \n Error: {}".format(
644 tc_name, result
645 )
646
647 step(
648 "Apply this route-map on R3 to set community under vrf RED/BLUE "
649 "while redistributing the prefixes into BGP"
650 )
651 temp = {}
652 for addr_type in ADDR_TYPES:
653 temp.update(
654 {
655 addr_type: {
656 "unicast": {
657 "redistribute": [
658 {
659 "redist_type": "static",
660 "attribute": {
661 "route-map": "rmap_XYZ_{}".format(addr_type)
662 },
663 }
664 ]
665 }
666 }
667 }
668 )
669
670 for vrf_name in ["RED", "BLUE"]:
671 redist_dict = {
672 "r3": {"bgp": [{"vrf": vrf_name, "local_as": 3, "address_family": temp}]}
673 }
674
675 result = create_router_bgp(tgen, topo, redist_dict)
676 assert result is True, "Testcase {} :Failed \n Error: {}".format(
677 tc_name, result
678 )
679
680 step(
681 "Verify that specific prefixes matched in route-map have community "
682 "attribute value 100:100 tagged"
683 )
684 input_dict_comm = {"community": COMM_VAL_1}
685 for addr_type in ADDR_TYPES:
686 result = verify_bgp_community(
687 tgen, addr_type, "r3", [NETWORK1_1[addr_type]], input_dict_comm, vrf="RED"
688 )
689 assert result is True, "Testcase {} : Failed \n Error {}".format(
690 tc_name, result
691 )
692
693 step(
694 "Configure a route-map for filtering the prefixes based on community "
695 "attribute while importing into default vrf"
696 )
697 for addr_type in ADDR_TYPES:
698 input_dict_rm = {
699 "r3": {
700 "route_maps": {
701 "rmap_IMP_{}".format(addr_type): [
702 {
703 "action": "permit",
704 "seq_id": 10,
705 "match": {"community_list": {"id": "COMM"}},
706 "set": {"community": {"num": COMM_VAL_2}},
707 }
708 ]
709 }
710 }
711 }
712 result = create_route_maps(tgen, input_dict_rm)
713 assert result is True, "Testcase {} : Failed \n Error: {}".format(
714 tc_name, result
715 )
716
717 step(
718 "Apply the route-map while Importing vrf RED/BLUE's prefixes into "
719 "GREEN vrf on router R3"
720 )
721 temp = {}
722 for vrf_name in ["RED", "BLUE"]:
723 for addr_type in ADDR_TYPES:
724 temp.update({addr_type: {"unicast": {"import": {"vrf": vrf_name}}}})
725
726 inport_dict = {
727 "r3": {"bgp": [{"vrf": "GREEN", "local_as": 3, "address_family": temp}]}
728 }
729
730 result = create_router_bgp(tgen, topo, inport_dict)
731 assert result is True, "Testcase {} :Failed \n Error: {}".format(
732 tc_name, result
733 )
734
735 temp = {}
736 for addr_type in ADDR_TYPES:
737 temp.update(
738 {
739 addr_type: {
740 "unicast": {
741 "import": {"vrf": "route-map rmap_IMP_{}".format(addr_type)}
742 }
743 }
744 }
745 )
746
747 inport_dict = {
748 "r3": {"bgp": [{"vrf": "GREEN", "local_as": 3, "address_family": temp}]}
749 }
750
751 result = create_router_bgp(tgen, topo, inport_dict)
752 assert result is True, "Testcase {} :Failed \n Error: {}".format(tc_name, result)
753
754 input_dict_comm = {"community": COMM_VAL_2}
755 step(
756 "Verify on R3 that only prefixes with community value {} in vrf RED "
757 "are imported to vrf GREEN. While importing, the community value "
758 "has been changed to {}".format(COMM_VAL_1, COMM_VAL_2)
759 )
760
761 for addr_type in ADDR_TYPES:
762 static_routes = {
763 "r3": {
764 "static_routes": [{"network": [NETWORK1_1[addr_type]], "vrf": "GREEN"}]
765 }
766 }
767
768 result = verify_bgp_rib(tgen, addr_type, "r3", static_routes)
769 assert result is True, "Testcase {} : Failed \n Error {}".format(
770 tc_name, result
771 )
772
773 result = verify_rib(tgen, addr_type, "r3", static_routes)
774 assert result is True, "Testcase {} : Failed \n Error {}".format(
775 tc_name, result
776 )
777
778 static_routes = {
779 "r3": {
780 "static_routes": [
781 {
782 "network": [
783 NETWORK2_1[addr_type],
784 NETWORK2_2[addr_type],
785 NETWORK1_2[addr_type],
786 ],
787 "vrf": "GREEN",
788 }
789 ]
790 }
791 }
792
793 result = verify_bgp_rib(tgen, addr_type, "r3", static_routes, expected=False)
794 assert (
795 result is not True
796 ), "Testcase {} : Failed \nError {}\n" "Routes {} still in BGP table".format(
797 tc_name, result, static_routes["r3"]["static_routes"][0]["network"]
798 )
799
800 result = verify_rib(tgen, addr_type, "r3", static_routes, expected=False)
801 assert (
802 result is not True
803 ), "Testcase {} : Failed Error {}" "Routes {} still in Route table".format(
804 tc_name, result, static_routes["r3"]["static_routes"][0]["network"]
805 )
806
807 result = verify_bgp_community(
808 tgen, addr_type, "r3", [NETWORK1_1[addr_type]], input_dict_comm, vrf="GREEN"
809 )
810 assert result is True, "Testcase {} : Failed \n Error {}".format(
811 tc_name, result
812 )
813
814 for action, value in zip(["Delete", "Add"], [True, False]):
815 step("{} import vrf RED/BLUE command one by one from vrf GREEN".format(action))
816 temp = {}
817 for vrf_name in ["RED", "BLUE"]:
818 for addr_type in ADDR_TYPES:
819 temp.update(
820 {
821 addr_type: {
822 "unicast": {"import": {"vrf": vrf_name, "delete": value}}
823 }
824 }
825 )
826
827 inport_dict = {
828 "r3": {"bgp": [{"vrf": "GREEN", "local_as": 3, "address_family": temp}]}
829 }
830
831 result = create_router_bgp(tgen, topo, inport_dict)
832 assert result is True, "Testcase {} :Failed \n Error: {}".format(
833 tc_name, result
834 )
835
836 step(
837 "Verify that when import vrf RED/BLUE is {} one by one, all "
838 "routes of respective vrf disappear from vrf GREEN without "
839 "affecting (BLUE/RED) routes".format(action.lower())
840 )
841 for addr_type in ADDR_TYPES:
842 static_routes = {
843 "r3": {
844 "static_routes": [
845 {"network": [NETWORK1_1[addr_type]], "vrf": "GREEN"}
846 ]
847 }
848 }
849
850 if value:
851 result = verify_bgp_rib(
852 tgen, addr_type, "r3", static_routes, expected=False
853 )
854 assert (
855 result is not True
856 ), "Testcase {} : Failed \nError {}\n" "Routes {} still in BGP table".format(
857 tc_name,
858 result,
859 static_routes["r3"]["static_routes"][0]["network"],
860 )
861
862 result = verify_rib(
863 tgen, addr_type, "r3", static_routes, expected=False
864 )
865 assert (
866 result is not True
867 ), "Testcase {} : Failed Error {}" "Routes {} still in Route table".format(
868 tc_name,
869 result,
870 static_routes["r3"]["static_routes"][0]["network"],
871 )
872 else:
873 result = verify_bgp_rib(tgen, addr_type, "r3", static_routes)
874 assert result is True, "Testcase {} : Failed \n Error {}".format(
875 tc_name, result
876 )
877
878 result = verify_rib(tgen, addr_type, "r3", static_routes)
879 assert result is True, "Testcase {} : Failed \n Error {}".format(
880 tc_name, result
881 )
882
883 for action, value in zip(["Delete", "Re-add"], [True, False]):
884 step(
885 "{} route-map IMP from global config when import and route-maps "
886 "are applied in vrf GREEN".format(action)
887 )
888 for addr_type in ADDR_TYPES:
889 input_dict_rm = {
890 "r3": {
891 "route_maps": {
892 "rmap_IMP_{}".format(addr_type): [
893 {
894 "action": "permit",
895 "seq_id": 10,
896 "match": {"community_list": {"id": "COMM"}},
897 "set": {"community": {"num": COMM_VAL_2}},
898 "delete": value,
899 }
900 ]
901 }
902 }
903 }
904 result = create_route_maps(tgen, input_dict_rm)
905 assert result is True, "Testcase {} : Failed \n Error: {}".format(
906 tc_name, result
907 )
908
909 step(
910 "Verify that when import vrf RED/BLUE is {} one by one, all "
911 "routes of respective vrf disappear from vrf GREEN without "
912 "affecting (BLUE/RED) routes".format(action.lower())
913 )
914 for addr_type in ADDR_TYPES:
915 static_routes = {
916 "r3": {
917 "static_routes": [
918 {"network": [NETWORK1_1[addr_type]], "vrf": "GREEN"}
919 ]
920 }
921 }
922
923 if value:
924 result = verify_bgp_rib(
925 tgen, addr_type, "r3", static_routes, expected=False
926 )
927 assert (
928 result is not True
929 ), "Testcase {} : Failed \nError {}\n" "Routes {} still in BGP table".format(
930 tc_name,
931 result,
932 static_routes["r3"]["static_routes"][0]["network"],
933 )
934
935 result = verify_rib(
936 tgen, addr_type, "r3", static_routes, expected=False
937 )
938 assert (
939 result is not True
940 ), "Testcase {} : Failed Error {}" "Routes {} still in Route table".format(
941 tc_name,
942 result,
943 static_routes["r3"]["static_routes"][0]["network"],
944 )
945 else:
946 result = verify_bgp_rib(tgen, addr_type, "r3", static_routes)
947 assert result is True, "Testcase {} : Failed \n Error {}".format(
948 tc_name, result
949 )
950
951 result = verify_rib(tgen, addr_type, "r3", static_routes)
952 assert result is True, "Testcase {} : Failed \n Error {}".format(
953 tc_name, result
954 )
955
956 write_test_footer(tc_name)
957
958
959def test_dynamic_import_routes_delete_static_route_p1(request):
960 """
961 Verify that deleting static routes from originating VRF also deletes
962 routes from other VRFs and peers.
963 """
964
965 tgen = get_topogen()
966 tc_name = request.node.name
967 write_test_header(tc_name)
968 reset_config_on_routers(tgen)
969 if tgen.routers_have_failure():
970 pytest.skip(tgen.errors)
971
972 step(
973 "Configure static routes on R3 for each tenant vrf and redistribute "
974 "in respective BGP instance"
975 )
976 vrf_list = VRF_LIST + ["default"]
977 for vrf_name, network in zip(
978 vrf_list, [NETWORK1_1, NETWORK2_1, NETWORK3_1, NETWORK1_2]
979 ):
980 step("Configure static route for VRF : {}".format(vrf_name))
981 for addr_type in ADDR_TYPES:
982 static_routes = {
983 "r3": {
984 "static_routes": [
985 {
986 "network": [network[addr_type]],
987 "next_hop": "blackhole",
988 "vrf": vrf_name,
989 }
990 ]
991 }
992 }
993
994 result = create_static_routes(tgen, static_routes)
995 assert result is True, "Testcase {} :Failed \n Error: {}".format(
996 tc_name, result
997 )
998
999 step("Redistribute static route on BGP VRF : {}".format(vrf_name))
1000 temp = {}
1001 for addr_type in ADDR_TYPES:
1002 temp.update(
1003 {addr_type: {"unicast": {"redistribute": [{"redist_type": "static"}]}}}
1004 )
1005
1006 redist_dict = {
1007 "r3": {"bgp": [{"vrf": vrf_name, "local_as": 3, "address_family": temp}]}
1008 }
1009
1010 result = create_router_bgp(tgen, topo, redist_dict)
1011 assert result is True, "Testcase {} :Failed \n Error: {}".format(
1012 tc_name, result
1013 )
1014
1015 for vrf_name, network in zip(vrf_list, [NETWORK1_1, NETWORK2_1, NETWORK3_1]):
1016 step(
1017 "Verify that R3 has installed redistributed routes in respective "
1018 "vrfs: {}".format(vrf_name)
1019 )
1020 for addr_type in ADDR_TYPES:
1021 static_routes = {
1022 "r3": {
1023 "static_routes": [
1024 {
1025 "network": [network[addr_type]],
1026 "next_hop": "blackhole",
1027 "vrf": vrf_name,
1028 }
1029 ]
1030 }
1031 }
1032
1033 result = verify_rib(tgen, addr_type, "r3", static_routes)
1034 assert result is True, "Testcase {} : Failed \n Error {}".format(
1035 tc_name, result
1036 )
1037
1038 step("Import routes among vrfs as mentioned below on router R3")
1039
1040 for vrf_name, vrf_import in zip(
1041 ["GREEN", "BLUE", "default"], ["RED", "GREEN", "BLUE"]
1042 ):
1043 temp = {}
1044 for addr_type in ADDR_TYPES:
1045 temp.update({addr_type: {"unicast": {"import": {"vrf": vrf_import}}}})
1046
1047 import_dict = {
1048 "r3": {"bgp": [{"vrf": vrf_name, "local_as": 3, "address_family": temp}]}
1049 }
1050
1051 result = create_router_bgp(tgen, topo, import_dict)
1052 assert result is True, "Testcase {} :Failed \n Error: {}".format(
1053 tc_name, result
1054 )
1055
1056 for vrf_name, vrf_import, installed, not_installed in zip(
1057 ["BLUE", "default"],
1058 ["GREEN", "BLUE"],
1059 [NETWORK3_1, NETWORK2_1],
1060 [NETWORK1_1, NETWORK3_1],
1061 ):
1062 step(
1063 "Verify that only locally originated routes of vrf {} are "
1064 "advertised to vrf {}".format(vrf_import, vrf_name)
1065 )
1066
1067 for addr_type in ADDR_TYPES:
1068 static_routes = {
1069 "r3": {
1070 "static_routes": [
1071 {"network": [installed[addr_type]], "vrf": vrf_name}
1072 ]
1073 }
1074 }
1075 result = verify_bgp_rib(tgen, addr_type, "r2", static_routes)
1076 assert result is True, "Testcase {} : Failed \n Error {}".format(
1077 tc_name, result
1078 )
1079
1080 result = verify_rib(tgen, addr_type, "r2", static_routes)
1081 assert result is True, "Testcase {} : Failed \n Error {}".format(
1082 tc_name, result
1083 )
1084
1085 step(
1086 "Verify that non local originated routes {} of vrf {} are "
1087 "not advertised to vrf {}".format(
1088 not_installed[addr_type], vrf_import, vrf_name
1089 )
1090 )
1091
1092 static_routes = {
1093 "r3": {
1094 "static_routes": [
1095 {"network": [not_installed[addr_type]], "vrf": vrf_name}
1096 ]
1097 }
1098 }
1099 result = verify_bgp_rib(
1100 tgen, addr_type, "r2", static_routes, expected=False
1101 )
1102 assert result is not True, (
1103 "Testcase {} : Failed \nError {}\n"
1104 "Routes {} still in BGP table".format(
1105 tc_name, result, static_routes["r2"]["static_routes"][0]["network"]
1106 )
1107 )
1108
1109 result = verify_rib(tgen, addr_type, "r2", static_routes, expected=False)
1110 assert (
1111 result is not True
1112 ), "Testcase {} : Failed Error {}" "Routes {} still in Route table".format(
1113 tc_name, result, static_routes["r2"]["static_routes"][0]["network"]
1114 )
1115
1116 step("Delete static routes from vrf RED")
1117 for addr_type in ADDR_TYPES:
1118 static_routes = {
1119 "r3": {
1120 "static_routes": [
1121 {
1122 "network": [NETWORK1_1[addr_type]],
1123 "next_hop": "blackhole",
1124 "vrf": "RED",
1125 "delete": True,
1126 }
1127 ]
1128 }
1129 }
1130
1131 result = create_static_routes(tgen, static_routes)
1132 assert result is True, "Testcase {} :Failed \n Error: {}".format(
1133 tc_name, result
1134 )
1135 step(
1136 "Verify on R2 and R3, that only vrf RED and GREEN's RIB/FIB withdraw "
1137 "deleted routes"
1138 )
1139 for dut in ["r2", "r3"]:
1140 step(
1141 "Verify on {}, that only vrf RED and GREEN's RIB/FIB withdraw "
1142 "deleted routes".format(dut)
1143 )
1144 for vrf_name in ["RED", "GREEN"]:
1145 for addr_type in ADDR_TYPES:
1146 static_routes = {
1147 "r3": {
1148 "static_routes": [
1149 {"network": [NETWORK1_1[addr_type]], "vrf": vrf_name}
1150 ]
1151 }
1152 }
1153 result = verify_bgp_rib(
1154 tgen, addr_type, "r2", static_routes, expected=False
1155 )
1156 assert (
1157 result is not True
1158 ), "Testcase {} : Failed \nError {}\n" "Routes {} still in BGP table".format(
1159 tc_name,
1160 result,
1161 static_routes["r2"]["static_routes"][0]["network"],
1162 )
1163
1164 result = verify_rib(
1165 tgen, addr_type, "r2", static_routes, expected=False
1166 )
1167 assert (
1168 result is not True
1169 ), "Testcase {} : Failed Error {}" "Routes {} still in Route table".format(
1170 tc_name,
1171 result,
1172 static_routes[dut]["static_routes"][0]["network"],
1173 )
1174
1175 step("Delete static routes from vrf BLUE")
1176 for addr_type in ADDR_TYPES:
1177 static_routes = {
1178 "r3": {
1179 "static_routes": [
1180 {
1181 "network": [NETWORK2_1[addr_type]],
1182 "next_hop": "blackhole",
1183 "vrf": "BLUE",
1184 "delete": True,
1185 }
1186 ]
1187 }
1188 }
1189
1190 result = create_static_routes(tgen, static_routes)
1191 assert result is True, "Testcase {} :Failed \n Error: {}".format(
1192 tc_name, result
1193 )
1194
1195 for dut in ["r2", "r3"]:
1196 step(
1197 "Verify on {}, that only default and BLUE vrf's RIB/FIB "
1198 "withdraw deleted routes".format(dut)
1199 )
1200 for vrf_name in ["BLUE", "default"]:
1201 for addr_type in ADDR_TYPES:
1202 static_routes = {
1203 "r3": {
1204 "static_routes": [
1205 {"network": [NETWORK2_1[addr_type]], "vrf": vrf_name}
1206 ]
1207 }
1208 }
1209 result = verify_bgp_rib(
1210 tgen, addr_type, dut, static_routes, expected=False
1211 )
1212 assert (
1213 result is not True
1214 ), "Testcase {} : Failed \nError {}\n" "Routes {} still in BGP table".format(
1215 tc_name,
1216 result,
1217 static_routes[dut]["static_routes"][0]["network"],
1218 )
1219
1220 result = verify_rib(tgen, addr_type, dut, static_routes, expected=False)
1221 assert (
1222 result is not True
1223 ), "Testcase {} : Failed Error {}" "Routes {} still in Route table".format(
1224 tc_name,
1225 result,
1226 static_routes[dut]["static_routes"][0]["network"],
1227 )
1228
1229 step("Delete static routes from vrf default")
1230 for addr_type in ADDR_TYPES:
1231 static_routes = {
1232 "r3": {
1233 "static_routes": [
1234 {
1235 "network": [NETWORK1_2[addr_type]],
1236 "next_hop": "blackhole",
1237 "delete": True,
1238 }
1239 ]
1240 }
1241 }
1242
1243 result = create_static_routes(tgen, static_routes)
1244 assert result is True, "Testcase {} :Failed \n Error: {}".format(
1245 tc_name, result
1246 )
1247
1248 for dut in ["r2", "r3"]:
1249 step(
1250 "Verify on {}, that only default vrf RIB/FIB withdraw deleted "
1251 "routes".format(dut)
1252 )
1253 for addr_type in ADDR_TYPES:
1254 static_routes = {
1255 "r3": {
1256 "static_routes": [
1257 {"network": [NETWORK1_2[addr_type]], "vrf": vrf_name}
1258 ]
1259 }
1260 }
1261 result = verify_bgp_rib(tgen, addr_type, dut, static_routes, expected=False)
1262 assert result is not True, (
1263 "Testcase {} : Failed \nError {}\n"
1264 "Routes {} still in BGP table".format(
1265 tc_name, result, static_routes[dut]["static_routes"][0]["network"]
1266 )
1267 )
1268
1269 result = verify_rib(tgen, addr_type, dut, static_routes, expected=False)
1270 assert result is not True, "Testcase {} : Failed \n Error {}".format(
1271 tc_name, result
1272 )
1273
1274 step("Add back all the routes that were deleted")
1275 for vrf_name, network in zip(
1276 vrf_list, [NETWORK1_1, NETWORK2_1, NETWORK3_1, NETWORK1_2]
1277 ):
1278 step("Configure static route for VRF : {}".format(vrf_name))
1279 for addr_type in ADDR_TYPES:
1280 static_routes = {
1281 "r3": {
1282 "static_routes": [
1283 {
1284 "network": [network[addr_type]],
1285 "next_hop": "blackhole",
1286 "vrf": vrf_name,
1287 }
1288 ]
1289 }
1290 }
1291
1292 result = create_static_routes(tgen, static_routes)
1293 assert result is True, "Testcase {} :Failed \n Error: {}".format(
1294 tc_name, result
1295 )
1296
1297 step("Redistribute static route on BGP VRF : {}".format(vrf_name))
1298 temp = {}
1299 for addr_type in ADDR_TYPES:
1300 temp.update(
1301 {addr_type: {"unicast": {"redistribute": [{"redist_type": "static"}]}}}
1302 )
1303
1304 redist_dict = {
1305 "r3": {"bgp": [{"vrf": vrf_name, "local_as": 3, "address_family": temp}]}
1306 }
1307
1308 result = create_router_bgp(tgen, topo, redist_dict)
1309 assert result is True, "Testcase {} :Failed \n Error: {}".format(
1310 tc_name, result
1311 )
1312
1313 for vrf_name, network in zip(vrf_list, [NETWORK1_1, NETWORK2_1, NETWORK3_1]):
1314 step(
1315 "Verify that R3 has installed redistributed routes in respective "
1316 "vrfs: {}".format(vrf_name)
1317 )
1318 for addr_type in ADDR_TYPES:
1319 static_routes = {
1320 "r3": {
1321 "static_routes": [
1322 {
1323 "network": [network[addr_type]],
1324 "next_hop": "blackhole",
1325 "vrf": vrf_name,
1326 }
1327 ]
1328 }
1329 }
1330
1331 result = verify_rib(tgen, addr_type, "r3", static_routes)
1332 assert result is True, "Testcase {} : Failed \n Error {}".format(
1333 tc_name, result
1334 )
1335
1336 write_test_footer(tc_name)
1337
1338
1339def test_dynamic_import_routes_add_delete_import_command_p1(request):
1340 """
1341 Verify that deleting and adding "import" command multiple times shows
1342 consistent results.
1343 """
1344
1345 tgen = get_topogen()
1346 tc_name = request.node.name
1347 write_test_header(tc_name)
1348 reset_config_on_routers(tgen)
1349 if tgen.routers_have_failure():
1350 pytest.skip(tgen.errors)
1351
1352 step(
1353 "Configure static routes on R2 for vrf RED and redistribute in "
1354 "respective BGP instance"
1355 )
1356 for addr_type in ADDR_TYPES:
1357 static_routes = {
1358 "r2": {
1359 "static_routes": [
1360 {
1361 "network": [NETWORK2_1[addr_type]],
1362 "next_hop": "blackhole",
1363 "vrf": "RED",
1364 }
1365 ]
1366 }
1367 }
1368
1369 result = create_static_routes(tgen, static_routes)
1370 assert result is True, "Testcase {} :Failed \n Error: {}".format(
1371 tc_name, result
1372 )
1373
1374 step("Redistribute static route on BGP VRF RED")
1375 temp = {}
1376 for addr_type in ADDR_TYPES:
1377 temp.update(
1378 {addr_type: {"unicast": {"redistribute": [{"redist_type": "static"}]}}}
1379 )
1380
1381 redist_dict = {
1382 "r2": {"bgp": [{"vrf": "RED", "local_as": 2, "address_family": temp}]}
1383 }
1384
1385 result = create_router_bgp(tgen, topo, redist_dict)
1386 assert result is True, "Testcase {} :Failed \n Error: {}".format(tc_name, result)
1387
1388 step("Verify that R2 has installed redistributed routes in respective " "vrfs only")
1389 for addr_type in ADDR_TYPES:
1390 static_routes = {
1391 "r2": {
1392 "static_routes": [{"network": [NETWORK2_1[addr_type]], "vrf": "RED"}]
1393 }
1394 }
1395 result = verify_bgp_rib(tgen, addr_type, "r2", static_routes)
1396 assert result is True, "Testcase {} : Failed \n Error {}".format(
1397 tc_name, result
1398 )
1399
1400 result = verify_rib(tgen, addr_type, "r2", static_routes)
1401 assert result is True, "Testcase {} : Failed \n Error {}".format(
1402 tc_name, result
1403 )
1404
1405 step("Import vrf RED's routes into vrf GREEN on R2")
1406 temp = {}
1407 for addr_type in ADDR_TYPES:
1408 temp.update({addr_type: {"unicast": {"import": {"vrf": "RED"}}}})
1409
1410 import_dict = {
1411 "r2": {"bgp": [{"vrf": "GREEN", "local_as": 2, "address_family": temp}]}
1412 }
1413 result = create_router_bgp(tgen, topo, import_dict)
1414 assert result is True, "Testcase {} :Failed \n Error: {}".format(tc_name, result)
1415
1416 step(
1417 "Verify on R2, that it installs imported routes from vrf RED to vrf "
1418 "GREEN's RIB/FIB"
1419 )
1420 for addr_type in ADDR_TYPES:
1421 static_routes = {
1422 "r2": {
1423 "static_routes": [{"network": [NETWORK2_1[addr_type]], "vrf": "GREEN"}]
1424 }
1425 }
1426 result = verify_bgp_rib(tgen, addr_type, "r2", static_routes)
1427 assert result is True, "Testcase {} : Failed \n Error {}".format(
1428 tc_name, result
1429 )
1430
1431 result = verify_rib(tgen, addr_type, "r2", static_routes)
1432 assert result is True, "Testcase {} : Failed \n Error {}".format(
1433 tc_name, result
1434 )
1435
1436 step("On R3 import routes from vrfs GREEN to default")
1437 temp = {}
1438 for addr_type in ADDR_TYPES:
1439 temp.update({addr_type: {"unicast": {"import": {"vrf": "GREEN"}}}})
1440
1441 import_dict = {"r3": {"bgp": [{"local_as": 3, "address_family": temp}]}}
1442 result = create_router_bgp(tgen, topo, import_dict)
1443 assert result is True, "Testcase {} :Failed \n Error: {}".format(tc_name, result)
1444
1445 step(
1446 "Verify that R2's vrf RED routes are now imported into vrf default "
1447 "of R3, next-hop pointing to vrf GREEN"
1448 )
1449 for addr_type in ADDR_TYPES:
1450 static_routes = {
1451 "r3": {"static_routes": [{"network": [NETWORK2_1[addr_type]]}]}
1452 }
1453
1454 next_hop_1 = topo["routers"]["r2"]["links"]["r3-link3"][addr_type].split("/")[0]
1455 result = verify_bgp_rib(
1456 tgen, addr_type, "r3", static_routes, next_hop=next_hop_1
1457 )
1458 assert result is True, "Testcase {} : Failed \n Error {}".format(
1459 tc_name, result
1460 )
1461
1462 result = verify_rib(tgen, addr_type, "r3", static_routes, next_hop=next_hop_1)
1463 assert result is True, "Testcase {} : Failed \n Error {}".format(
1464 tc_name, result
1465 )
1466
1467 step(
1468 "Delete import command from R3's default vrf instance for both "
1469 "address-families 1 by 1 (ipv4/ipv6)"
1470 )
1471 temp = {}
1472 for addr_type in ADDR_TYPES:
1473 temp.update(
1474 {addr_type: {"unicast": {"import": {"vrf": "GREEN", "delete": True}}}}
1475 )
1476
1477 import_dict = {"r3": {"bgp": [{"local_as": 3, "address_family": temp}]}}
1478 result = create_router_bgp(tgen, topo, import_dict)
1479 assert result is True, "Testcase {} :Failed \n Error: {}".format(tc_name, result)
1480
1481 step(
1482 "Verify that R2's vrf RED routes are now removed from vrf "
1483 "default on R3, however vrf GREEN still retains those"
1484 )
1485 for addr_type in ADDR_TYPES:
1486 static_routes = {
1487 "r3": {"static_routes": [{"network": [NETWORK2_1[addr_type]]}]}
1488 }
1489 result = verify_bgp_rib(tgen, addr_type, "r3", static_routes, expected=False)
1490 assert (
1491 result is not True
1492 ), "Testcase {} : Failed \nError {}\n" "Routes {} still in BGP table".format(
1493 tc_name, result, static_routes["r3"]["static_routes"][0]["network"]
1494 )
1495
1496 result = verify_rib(tgen, addr_type, "r3", static_routes, expected=False)
1497 assert result is not True, "Testcase {} : Failed \n Error {}".format(
1498 tc_name, result
1499 )
1500
1501 step(
1502 "Delete import command from R2's vrf GREEN instance for both "
1503 "address-families 1 by 1 (ipv4/ipv6)"
1504 )
1505 temp = {}
1506 for addr_type in ADDR_TYPES:
1507 temp.update(
1508 {addr_type: {"unicast": {"import": {"vrf": "RED", "delete": True}}}}
1509 )
1510
1511 import_dict = {
1512 "r2": {"bgp": [{"vrf": "GREEN", "local_as": 2, "address_family": temp}]}
1513 }
1514 result = create_router_bgp(tgen, topo, import_dict)
1515 assert result is True, "Testcase {} :Failed \n Error: {}".format(tc_name, result)
1516 step(
1517 "Verify that R2's vrf RED routes are now removed from vrf GREEN "
1518 "on R2 & R3 as well"
1519 )
1520 for dut in ["r2", "r3"]:
1521 for addr_type in ADDR_TYPES:
1522 static_routes = {
1523 "r2": {
1524 "static_routes": [
1525 {"network": [NETWORK2_1[addr_type]], "vrf": "GREEN"}
1526 ]
1527 }
1528 }
1529 result = verify_bgp_rib(tgen, addr_type, dut, static_routes, expected=False)
1530 assert result is not True, (
1531 "Testcase {} : Failed \nError {}\n"
1532 "Routes {} still in BGP table".format(
1533 tc_name, result, static_routes[dut]["static_routes"][0]["network"]
1534 )
1535 )
1536
1537 result = verify_rib(tgen, addr_type, dut, static_routes, expected=False)
1538 assert (
1539 result is not True
1540 ), "Testcase {} : Failed Error {}" "Routes {} still in Route table".format(
1541 tc_name, result, static_routes[dut]["static_routes"][0]["network"]
1542 )
1543
1544 step(
1545 "Add import command from R3's default vrf instance for both "
1546 "address-families 1 by 1 (ipv4/ipv6)"
1547 )
1548 temp = {}
1549 for addr_type in ADDR_TYPES:
1550 temp.update({addr_type: {"unicast": {"import": {"vrf": "GREEN"}}}})
1551
1552 import_dict = {"r3": {"bgp": [{"local_as": 3, "address_family": temp}]}}
1553 result = create_router_bgp(tgen, topo, import_dict)
1554 assert result is True, "Testcase {} :Failed \n Error: {}".format(tc_name, result)
1555
1556 step("Verify that there are no routes installed on R3's vrf default " "RIB/FIB.")
1557 for addr_type in ADDR_TYPES:
1558 static_routes = {
1559 "r3": {"static_routes": [{"network": [NETWORK2_1[addr_type]]}]}
1560 }
1561 result = verify_bgp_rib(tgen, addr_type, "r3", static_routes, expected=False)
1562 assert (
1563 result is not True
1564 ), "Testcase {} : Failed \nError {}\n" "Routes {} still in BGP table".format(
1565 tc_name, result, static_routes["r3"]["static_routes"][0]["network"]
1566 )
1567
1568 result = verify_rib(tgen, addr_type, "r3", static_routes, expected=False)
1569 assert result is not True, "Testcase {} : Failed \n Error {}".format(
1570 tc_name, result
1571 )
1572
1573 step(
1574 "Add import command from R2's vrf GREEN instance for both "
1575 "address-families 1 by 1 (ipv4/ipv6)."
1576 )
1577 temp = {}
1578 for addr_type in ADDR_TYPES:
1579 temp.update({addr_type: {"unicast": {"import": {"vrf": "RED"}}}})
1580
1581 import_dict = {
1582 "r2": {"bgp": [{"vrf": "GREEN", "local_as": 2, "address_family": temp}]}
1583 }
1584 result = create_router_bgp(tgen, topo, import_dict)
1585 assert result is True, "Testcase {} :Failed \n Error: {}".format(tc_name, result)
1586
1587 step(
1588 "Verify that R2's vrf RED routes are now imported into vrf "
1589 "default of R3, next-hop pointing to vrf GREEN"
1590 )
1591 for dut in ["r2", "r3"]:
1592 for addr_type in ADDR_TYPES:
1593 static_routes = {
1594 "r2": {
1595 "static_routes": [
1596 {"network": [NETWORK2_1[addr_type]], "vrf": "GREEN"}
1597 ]
1598 }
1599 }
1600 if dut == "r3":
1601 next_hop_1 = topo["routers"]["r2"]["links"]["r3-link3"][
1602 addr_type
1603 ].split("/")[0]
1604 result = verify_bgp_rib(
1605 tgen, addr_type, dut, static_routes, next_hop=next_hop_1
1606 )
1607 else:
1608 result = verify_bgp_rib(tgen, addr_type, dut, static_routes)
1609 assert result is True, "Testcase {} : Failed \n Error {}".format(
1610 tc_name, result
1611 )
1612
1613 if dut == "r3":
1614 result = verify_rib(
1615 tgen, addr_type, dut, static_routes, next_hop=next_hop_1
1616 )
1617 else:
1618 result = verify_rib(tgen, addr_type, dut, static_routes)
1619
1620 assert result is True, "Testcase {} : Failed \n Error {}".format(
1621 tc_name, result
1622 )
1623
1624 step(
1625 "Delete import command from R3's default vrf instance for both "
1626 "address-families 1 by 1 (ipv4/ipv6)."
1627 )
1628 temp = {}
1629 for addr_type in ADDR_TYPES:
1630 temp.update(
1631 {addr_type: {"unicast": {"import": {"vrf": "GREEN", "delete": True}}}}
1632 )
1633
1634 import_dict = {"r3": {"bgp": [{"local_as": 3, "address_family": temp}]}}
1635 result = create_router_bgp(tgen, topo, import_dict)
1636 assert result is True, "Testcase {} :Failed \n Error: {}".format(tc_name, result)
1637
1638 step(
1639 "Verify that R2's vrf RED routes are now removed from vrf "
1640 "default on R3, however vrf GREEN still retains those."
1641 )
1642 for addr_type in ADDR_TYPES:
1643 static_routes = {
1644 "r2": {
1645 "static_routes": [{"network": [NETWORK2_1[addr_type]], "vrf": "GREEN"}]
1646 }
1647 }
1648 result = verify_bgp_rib(tgen, addr_type, "r3", static_routes)
1649 assert result is True, "Testcase {} : Failed \n Error {}".format(
1650 tc_name, result
1651 )
1652
1653 result = verify_rib(tgen, addr_type, "r3", static_routes)
1654 assert result is True, "Testcase {} : Failed \n Error {}".format(
1655 tc_name, result
1656 )
1657
1658 static_routes = {
1659 "r2": {"static_routes": [{"network": [NETWORK2_1[addr_type]]}]}
1660 }
1661 result = verify_bgp_rib(tgen, addr_type, "r3", static_routes, expected=False)
1662 assert (
1663 result is not True
1664 ), "Testcase {} : Failed \nError {}\n" "Routes {} still in BGP table".format(
1665 tc_name, result, static_routes["r3"]["static_routes"][0]["network"]
1666 )
1667
1668 result = verify_rib(tgen, addr_type, "r3", static_routes, expected=False)
1669 assert result is not True, "Testcase {} : Failed \n Error {}".format(
1670 tc_name, result
1671 )
1672
1673 step("Delete redistribute static from R2 for vrf RED")
1674 temp = {}
1675 for addr_type in ADDR_TYPES:
1676 temp.update(
1677 {
1678 addr_type: {
1679 "unicast": {
1680 "redistribute": [{"redist_type": "static", "delete": True}]
1681 }
1682 }
1683 }
1684 )
1685
1686 redist_dict = {
1687 "r2": {"bgp": [{"vrf": "RED", "local_as": 2, "address_family": temp}]}
1688 }
1689
1690 result = create_router_bgp(tgen, topo, redist_dict)
1691 assert result is True, "Testcase {} :Failed \n Error: {}".format(tc_name, result)
1692
1693 step(
1694 "Verify that R2's vrf RED routes are now removed from vrf GREEN "
1695 "on R2 & R3 as well."
1696 )
1697 for dut in ["r2", "r3"]:
1698 for addr_type in ADDR_TYPES:
1699 static_routes = {
1700 "r2": {
1701 "static_routes": [
1702 {"network": [NETWORK2_1[addr_type]], "vrf": "GREEN"}
1703 ]
1704 }
1705 }
1706 result = verify_bgp_rib(tgen, addr_type, dut, static_routes, expected=False)
1707 assert result is not True, (
1708 "Testcase {} : Failed \nError {}\n"
1709 "Routes {} still in BGP table".format(
1710 tc_name, result, static_routes[dut]["static_routes"][0]["network"]
1711 )
1712 )
1713
1714 result = verify_rib(tgen, addr_type, dut, static_routes, expected=False)
1715 assert (
1716 result is not True
1717 ), "Testcase {} : Failed Error {}" "Routes {} still in Route table".format(
1718 tc_name, result, static_routes[dut]["static_routes"][0]["network"]
1719 )
1720
1721 step(
1722 "Add import command from R3's default vrf instance for both "
1723 "address-families 1 by 1 (ipv4/ipv6)."
1724 )
1725 temp = {}
1726 for addr_type in ADDR_TYPES:
1727 temp.update({addr_type: {"unicast": {"import": {"vrf": "GREEN"}}}})
1728
1729 import_dict = {"r3": {"bgp": [{"local_as": 3, "address_family": temp}]}}
1730 result = create_router_bgp(tgen, topo, import_dict)
1731 assert result is True, "Testcase {} :Failed \n Error: {}".format(tc_name, result)
1732
1733 step("Verify that there are no routes installed on R3's vrf default " "RIB/FIB")
1734 for addr_type in ADDR_TYPES:
1735 static_routes = {
1736 "r3": {"static_routes": [{"network": [NETWORK2_1[addr_type]]}]}
1737 }
1738 result = verify_bgp_rib(tgen, addr_type, "r3", static_routes, expected=False)
1739 assert (
1740 result is not True
1741 ), "Testcase {} : Failed \nError {}\n" "Routes {} still in BGP table".format(
1742 tc_name, result, static_routes["r3"]["static_routes"][0]["network"]
1743 )
1744
1745 result = verify_rib(tgen, addr_type, "r3", static_routes, expected=False)
1746 assert result is not True, "Testcase {} : Failed \n Error {}".format(
1747 tc_name, result
1748 )
1749
1750 step("Add redistribute static from R2 for vrf RED")
1751 temp = {}
1752 for addr_type in ADDR_TYPES:
1753 temp.update(
1754 {addr_type: {"unicast": {"redistribute": [{"redist_type": "static"}]}}}
1755 )
1756
1757 redist_dict = {
1758 "r2": {"bgp": [{"vrf": "RED", "local_as": 2, "address_family": temp}]}
1759 }
1760
1761 result = create_router_bgp(tgen, topo, redist_dict)
1762 assert result is True, "Testcase {} :Failed \n Error: {}".format(tc_name, result)
1763
1764 step(
1765 "Verify that R2's vrf RED routes are now imported into vrf "
1766 "default of R3, next-hop pointing to vrf GREEN"
1767 )
1768 for addr_type in ADDR_TYPES:
1769 static_routes = {
1770 "r3": {"static_routes": [{"network": [NETWORK2_1[addr_type]]}]}
1771 }
1772 next_hop_1 = topo["routers"]["r2"]["links"]["r3-link3"][addr_type].split("/")[0]
1773 result = verify_bgp_rib(
1774 tgen, addr_type, "r3", static_routes, next_hop=next_hop_1
1775 )
1776 assert result is True, "Testcase {} : Failed \n Error {}".format(
1777 tc_name, result
1778 )
1779
1780 result = verify_rib(tgen, addr_type, "r3", static_routes, next_hop=next_hop_1)
1781 assert result is True, "Testcase {} : Failed \n Error {}".format(
1782 tc_name, result
1783 )
1784
1785 write_test_footer(tc_name)
1786
1787
1788if __name__ == "__main__":
1789 args = ["-s"] + sys.argv[1:]
1790 sys.exit(pytest.main(args))