]> git.proxmox.com Git - mirror_frr.git/blob - tests/topotests/bgp_vrf_lite_best_path_test/test_bgp_vrf_lite_best_path_topo1.py
doc: Add `show ipv6 rpf X:X::X:X` command to docs
[mirror_frr.git] / tests / topotests / bgp_vrf_lite_best_path_test / test_bgp_vrf_lite_best_path_topo1.py
1 #!/usr/bin/env python
2
3 #
4 # Copyright (c) 2020 by VMware, Inc. ("VMware")
5 # Used Copyright (c) 2018 by Network Device Education Foundation,
6 # Inc. ("NetDEF") in this file.
7 #
8 # Permission to use, copy, modify, and/or distribute this software
9 # for any purpose with or without fee is hereby granted, provided
10 # that the above copyright notice and this permission notice appear
11 # in all copies.
12 #
13 # THE SOFTWARE IS PROVIDED "AS IS" AND VMWARE DISCLAIMS ALL WARRANTIES
14 # WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
15 # MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL VMWARE BE LIABLE FOR
16 # ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY
17 # DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
18 # WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
19 # ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE
20 # OF THIS SOFTWARE.
21 #
22
23 """
24 Following tests are covered to test BGP VRF Lite:
25
26 1. Verify BGP best path selection algorithm works fine when
27 routes are imported from ISR to default vrf and vice versa.
28 """
29
30 import os
31 import sys
32 import time
33 import pytest
34 import platform
35
36 # Save the Current Working Directory to find configuration files.
37 CWD = os.path.dirname(os.path.realpath(__file__))
38 sys.path.append(os.path.join(CWD, "../"))
39 sys.path.append(os.path.join(CWD, "../lib/"))
40
41 # Required to instantiate the topology builder class.
42
43 # pylint: disable=C0413
44 # Import topogen and topotest helpers
45 from lib.topogen import Topogen, get_topogen
46 from lib.topotest import version_cmp
47
48 from lib.common_config import (
49 start_topology,
50 write_test_header,
51 check_address_types,
52 write_test_footer,
53 step,
54 create_route_maps,
55 create_prefix_lists,
56 check_router_status,
57 get_frr_ipv6_linklocal,
58 shutdown_bringup_interface,
59 )
60
61 from lib.topolog import logger
62 from lib.bgp import (
63 verify_bgp_convergence,
64 create_router_bgp,
65 verify_bgp_community,
66 verify_bgp_rib,
67 clear_bgp,
68 verify_best_path_as_per_bgp_attribute
69 )
70 from lib.topojson import build_config_from_json
71
72
73 pytestmark = [pytest.mark.bgpd, pytest.mark.staticd]
74
75 # Global variables
76 NETWORK1_1 = {"ipv4": "11.11.11.1/32", "ipv6": "11:11::1/128"}
77 NETWORK1_2 = {"ipv4": "11.11.11.11/32", "ipv6": "11:11::11/128"}
78 NETWORK1_3 = {"ipv4": "10.10.10.10/32", "ipv6": "10:10::10/128"}
79 NETWORK1_4 = {"ipv4": "10.10.10.100/32", "ipv6": "10:10::100/128"}
80
81 NETWORK2_1 = {"ipv4": "22.22.22.2/32", "ipv6": "22:22::2/128"}
82 NETWORK2_2 = {"ipv4": "22.22.22.22/32", "ipv6": "22:22::22/128"}
83 NETWORK2_3 = {"ipv4": "20.20.20.20/32", "ipv6": "20:20::20/128"}
84 NETWORK2_4 = {"ipv4": "20.20.20.200/32", "ipv6": "20:20::200/128"}
85
86 NETWORK3_1 = {"ipv4": "30.30.30.3/32", "ipv6": "30:30::3/128"}
87 NETWORK3_2 = {"ipv4": "30.30.30.30/32", "ipv6": "30:30::30/128"}
88 NETWORK3_3 = {"ipv4": "50.50.50.5/32", "ipv6": "50:50::5/128"}
89 NETWORK3_4 = {"ipv4": "50.50.50.50/32", "ipv6": "50:50::50/128"}
90
91 NETWORK4_1 = {"ipv4": "40.40.40.4/32", "ipv6": "40:40::4/128"}
92 NETWORK4_2 = {"ipv4": "40.40.40.40/32", "ipv6": "40:40::40/128"}
93 NETWORK4_3 = {"ipv4": "50.50.50.5/32", "ipv6": "50:50::5/128"}
94 NETWORK4_4 = {"ipv4": "50.50.50.50/32", "ipv6": "50:50::50/128"}
95 NEXT_HOP_IP = {"ipv4": "Null0", "ipv6": "Null0"}
96 LOOPBACK_1 = {
97 "ipv4": "10.0.0.7/24",
98 "ipv6": "fd00:0:0:1::7/64",
99 "ipv4_mask": "255.255.255.0",
100 "ipv6_mask": None,
101 }
102 LOOPBACK_2 = {
103 "ipv4": "10.0.0.16/24",
104 "ipv6": "fd00:0:0:3::5/64",
105 "ipv4_mask": "255.255.255.0",
106 "ipv6_mask": None,
107 }
108 PREFERRED_NEXT_HOP = "global"
109
110
111 def setup_module(mod):
112 """
113 Sets up the pytest environment
114
115 * `mod`: module name
116 """
117
118 testsuite_run_time = time.asctime(time.localtime(time.time()))
119 logger.info("Testsuite start time: {}".format(testsuite_run_time))
120 logger.info("=" * 40)
121
122 logger.info("Running setup_module to create topology")
123
124 # This function initiates the topology build with Topogen...
125 json_file = "{}/bgp_vrf_lite_best_path_topo1.json".format(CWD)
126 tgen = Topogen(json_file, mod.__name__)
127 global topo
128 topo = tgen.json_topo
129 # ... and here it calls Mininet initialization functions.
130
131 # Starting topology, create tmp files which are loaded to routers
132 # to start daemons and then start routers
133 start_topology(tgen)
134
135 # Run these tests for kernel version 4.19 or above
136 if version_cmp(platform.release(), "4.19") < 0:
137 error_msg = (
138 "BGP vrf dynamic route leak tests will not run "
139 '(have kernel "{}", but it requires >= 4.19)'.format(platform.release())
140 )
141 pytest.skip(error_msg)
142
143 # Creating configuration from JSON
144 build_config_from_json(tgen, topo)
145
146 global BGP_CONVERGENCE
147 global ADDR_TYPES
148 ADDR_TYPES = check_address_types()
149
150 BGP_CONVERGENCE = verify_bgp_convergence(tgen, topo)
151 assert BGP_CONVERGENCE is True, "setup_module : Failed \n Error: {}".format(
152 BGP_CONVERGENCE
153 )
154
155 logger.info("Running setup_module() done")
156
157
158 def teardown_module():
159 """Teardown the pytest environment"""
160
161 logger.info("Running teardown_module to delete topology")
162
163 tgen = get_topogen()
164
165 # Stop toplogy and Remove tmp files
166 tgen.stop_topology()
167
168 logger.info(
169 "Testsuite end time: {}".format(time.asctime(time.localtime(time.time())))
170 )
171 logger.info("=" * 40)
172
173
174 #####################################################
175 #
176 # Testcases
177 #
178 #####################################################
179
180
181 def disable_route_map_to_prefer_global_next_hop(tgen, topo):
182 """
183 This API is to remove prefer global route-map applied on neighbors
184
185 Parameter:
186 ----------
187 * `tgen` : Topogen object
188 * `topo` : Input JSON data
189
190 Returns:
191 --------
192 True/errormsg
193
194 """
195
196 logger.info("Remove prefer-global rmap applied on neighbors")
197 input_dict = {
198 "r1": {
199 "bgp": [
200 {
201 "local_as": "100",
202 "vrf": "ISR",
203 "address_family": {
204 "ipv6": {
205 "unicast": {
206 "neighbor": {
207 "r2": {
208 "dest_link": {
209 "r1-link1": {
210 "route_maps": [
211 {
212 "name": "rmap_global",
213 "direction": "in",
214 "delete": True,
215 }
216 ]
217 }
218 }
219 }
220 }
221 }
222 }
223 },
224 },
225 {
226 "local_as": "100",
227 "address_family": {
228 "ipv6": {
229 "unicast": {
230 "neighbor": {
231 "r3": {
232 "dest_link": {
233 "r1-link1": {
234 "route_maps": [
235 {
236 "name": "rmap_global",
237 "direction": "in",
238 "delete": True,
239 }
240 ]
241 }
242 }
243 }
244 }
245 }
246 }
247 },
248 },
249 {
250 "local_as": "100",
251 "address_family": {
252 "ipv6": {
253 "unicast": {
254 "neighbor": {
255 "r4": {
256 "dest_link": {
257 "r1-link1": {
258 "route_maps": [
259 {
260 "name": "rmap_global",
261 "direction": "in",
262 "delete": True,
263 }
264 ]
265 }
266 }
267 }
268 }
269 }
270 }
271 },
272 },
273 ]
274 },
275 "r2": {
276 "bgp": [
277 {
278 "local_as": "100",
279 "vrf": "ISR",
280 "address_family": {
281 "ipv6": {
282 "unicast": {
283 "neighbor": {
284 "r1": {
285 "dest_link": {
286 "r2-link1": {
287 "route_maps": [
288 {
289 "name": "rmap_global",
290 "direction": "in",
291 "delete": True,
292 }
293 ]
294 }
295 }
296 }
297 }
298 }
299 }
300 },
301 },
302 {
303 "local_as": "100",
304 "address_family": {
305 "ipv6": {
306 "unicast": {
307 "neighbor": {
308 "r3": {
309 "dest_link": {
310 "r2-link1": {
311 "route_maps": [
312 {
313 "name": "rmap_global",
314 "direction": "in",
315 "delete": True,
316 }
317 ]
318 }
319 }
320 }
321 }
322 }
323 }
324 },
325 },
326 {
327 "local_as": "100",
328 "address_family": {
329 "ipv6": {
330 "unicast": {
331 "neighbor": {
332 "r4": {
333 "dest_link": {
334 "r2-link1": {
335 "route_maps": [
336 {
337 "name": "rmap_global",
338 "direction": "in",
339 "delete": True,
340 }
341 ]
342 }
343 }
344 }
345 }
346 }
347 }
348 },
349 },
350 ]
351 },
352 "r3": {
353 "bgp": [
354 {
355 "local_as": "300",
356 "address_family": {
357 "ipv6": {
358 "unicast": {
359 "neighbor": {
360 "r1": {
361 "dest_link": {
362 "r3-link1": {
363 "route_maps": [
364 {
365 "name": "rmap_global",
366 "direction": "in",
367 "delete": True,
368 }
369 ]
370 }
371 }
372 }
373 }
374 }
375 }
376 },
377 },
378 {
379 "local_as": "300",
380 "address_family": {
381 "ipv6": {
382 "unicast": {
383 "neighbor": {
384 "r2": {
385 "dest_link": {
386 "r3-link1": {
387 "route_maps": [
388 {
389 "name": "rmap_global",
390 "direction": "in",
391 "delete": True,
392 }
393 ]
394 }
395 }
396 }
397 }
398 }
399 }
400 },
401 },
402 ]
403 },
404 "r4": {
405 "bgp": [
406 {
407 "local_as": "400",
408 "address_family": {
409 "ipv6": {
410 "unicast": {
411 "neighbor": {
412 "r1": {
413 "dest_link": {
414 "r4-link1": {
415 "route_maps": [
416 {
417 "name": "rmap_global",
418 "direction": "in",
419 "delete": True,
420 }
421 ]
422 }
423 }
424 }
425 }
426 }
427 }
428 },
429 },
430 {
431 "local_as": "400",
432 "address_family": {
433 "ipv6": {
434 "unicast": {
435 "neighbor": {
436 "r2": {
437 "dest_link": {
438 "r4-link1": {
439 "route_maps": [
440 {
441 "name": "rmap_global",
442 "direction": "in",
443 "delete": True,
444 }
445 ]
446 }
447 }
448 }
449 }
450 }
451 }
452 },
453 },
454 ]
455 },
456 }
457
458 result = create_router_bgp(tgen, topo, input_dict)
459 assert result is True, "Testcase :Failed \n Error: {}".format(result)
460
461 return True
462
463
464 def test_bgp_best_path_with_dynamic_import_p0(request):
465 """
466 1.5.6. Verify BGP best path selection algorithm works fine when
467 routes are imported from ISR to default vrf and vice versa.
468 """
469
470 tgen = get_topogen()
471 tc_name = request.node.name
472 write_test_header(tc_name)
473 build_config_from_json(tgen, topo)
474
475 if tgen.routers_have_failure():
476 check_router_status(tgen)
477
478 for addr_type in ADDR_TYPES:
479
480 step(
481 "Redistribute configured static routes into BGP process" " on R1/R2 and R3"
482 )
483
484 input_dict_1 = {}
485 DUT = ["r1", "r2", "r3", "r4"]
486 VRFS = ["ISR", "ISR", "default", "default"]
487 AS_NUM = [100, 100, 300, 400]
488
489 for dut, vrf, as_num in zip(DUT, VRFS, AS_NUM):
490 temp = {dut: {"bgp": []}}
491 input_dict_1.update(temp)
492
493 temp[dut]["bgp"].append(
494 {
495 "local_as": as_num,
496 "vrf": vrf,
497 "address_family": {
498 addr_type: {
499 "unicast": {"redistribute": [{"redist_type": "static"}]}
500 }
501 },
502 }
503 )
504
505 result = create_router_bgp(tgen, topo, input_dict_1)
506 assert result is True, "Testcase {} :Failed \n Error: {}".format(
507 tc_name, result
508 )
509
510 for addr_type in ADDR_TYPES:
511
512 step("Import from default vrf into vrf ISR on R1 and R2 as below")
513
514 input_dict_vrf = {}
515 DUT = ["r1", "r2"]
516 VRFS = ["ISR", "ISR"]
517 AS_NUM = [100, 100]
518
519 for dut, vrf, as_num in zip(DUT, VRFS, AS_NUM):
520 temp = {dut: {"bgp": []}}
521 input_dict_vrf.update(temp)
522
523 temp[dut]["bgp"].append(
524 {
525 "local_as": as_num,
526 "vrf": vrf,
527 "address_family": {
528 addr_type: {"unicast": {"import": {"vrf": "default"}}}
529 },
530 }
531 )
532
533 result = create_router_bgp(tgen, topo, input_dict_vrf)
534 assert result is True, "Testcase {} : Failed \n Error: {}".format(
535 tc_name, result
536 )
537
538 input_dict_default = {}
539 DUT = ["r1", "r2"]
540 VRFS = ["default", "default"]
541 AS_NUM = [100, 100]
542
543 for dut, vrf, as_num in zip(DUT, VRFS, AS_NUM):
544 temp = {dut: {"bgp": []}}
545 input_dict_default.update(temp)
546
547 temp[dut]["bgp"].append(
548 {
549 "local_as": as_num,
550 "vrf": vrf,
551 "address_family": {
552 addr_type: {"unicast": {"import": {"vrf": "ISR"}}}
553 },
554 }
555 )
556
557 result = create_router_bgp(tgen, topo, input_dict_default)
558 assert result is True, "Testcase {} : Failed \n Error: {}".format(
559 tc_name, result
560 )
561
562 step(
563 "Verify ECMP/Next-hop/Imported routes Vs Locally originated "
564 "routes/eBGP routes vs iBGP routes --already covered in almost"
565 " all tests"
566 )
567
568 for addr_type in ADDR_TYPES:
569
570 step("Verify Pre-emption")
571
572 input_routes_r3 = {
573 "r3": {"static_routes": [{"network": [NETWORK3_3[addr_type]]}]}
574 }
575
576 intf_r3_r1 = topo["routers"]["r3"]["links"]["r1-link1"]["interface"]
577 intf_r4_r1 = topo["routers"]["r4"]["links"]["r1-link1"]["interface"]
578
579 if addr_type == "ipv6" and "link_local" in PREFERRED_NEXT_HOP:
580 nh_r3_r1 = get_frr_ipv6_linklocal(tgen, "r3", intf=intf_r3_r1)
581 nh_r4_r1 = get_frr_ipv6_linklocal(tgen, "r4", intf=intf_r4_r1)
582 else:
583 nh_r3_r1 = topo["routers"]["r3"]["links"]["r1-link1"][addr_type].split("/")[
584 0
585 ]
586 nh_r4_r1 = topo["routers"]["r4"]["links"]["r1-link1"][addr_type].split("/")[
587 0
588 ]
589
590 result = verify_bgp_rib(
591 tgen, addr_type, "r1", input_routes_r3, next_hop=[nh_r4_r1]
592 )
593 assert result is True, "Testcase {} : Failed \n Error {}".format(
594 tc_name, result
595 )
596
597 step("Shutdown interface connected to r1 from r4:")
598 shutdown_bringup_interface(tgen, "r4", intf_r4_r1, False)
599
600 for addr_type in ADDR_TYPES:
601
602 input_routes_r3 = {
603 "r3": {"static_routes": [{"network": [NETWORK3_3[addr_type]]}]}
604 }
605
606 intf_r3_r1 = topo["routers"]["r3"]["links"]["r1-link1"]["interface"]
607 intf_r4_r1 = topo["routers"]["r4"]["links"]["r1-link1"]["interface"]
608
609 if addr_type == "ipv6" and "link_local" in PREFERRED_NEXT_HOP:
610 nh_r3_r1 = get_frr_ipv6_linklocal(tgen, "r3", intf=intf_r3_r1)
611 nh_r4_r1 = get_frr_ipv6_linklocal(tgen, "r4", intf=intf_r4_r1)
612 else:
613 nh_r3_r1 = topo["routers"]["r3"]["links"]["r1-link1"][addr_type].split("/")[
614 0
615 ]
616 nh_r4_r1 = topo["routers"]["r4"]["links"]["r1-link1"][addr_type].split("/")[
617 0
618 ]
619
620 step("Verify next-hop is changed")
621 result = verify_bgp_rib(
622 tgen, addr_type, "r1", input_routes_r3, next_hop=[nh_r3_r1]
623 )
624 assert result is True, "Testcase {} : Failed \n Error {}".format(
625 tc_name, result
626 )
627
628 step("Bringup interface connected to r1 from r4:")
629 shutdown_bringup_interface(tgen, "r4", intf_r4_r1, True)
630
631 for addr_type in ADDR_TYPES:
632
633 input_routes_r3 = {
634 "r3": {"static_routes": [{"network": [NETWORK3_3[addr_type]]}]}
635 }
636
637 intf_r3_r1 = topo["routers"]["r3"]["links"]["r1-link1"]["interface"]
638 intf_r4_r1 = topo["routers"]["r4"]["links"]["r1-link1"]["interface"]
639
640 if addr_type == "ipv6" and "link_local" in PREFERRED_NEXT_HOP:
641 nh_r3_r1 = get_frr_ipv6_linklocal(tgen, "r3", intf=intf_r3_r1)
642 nh_r4_r1 = get_frr_ipv6_linklocal(tgen, "r4", intf=intf_r4_r1)
643 else:
644 nh_r3_r1 = topo["routers"]["r3"]["links"]["r1-link1"][addr_type].split("/")[
645 0
646 ]
647 nh_r4_r1 = topo["routers"]["r4"]["links"]["r1-link1"][addr_type].split("/")[
648 0
649 ]
650
651 step("Verify next-hop is not chnaged aftr shutdown:")
652 result = verify_bgp_rib(
653 tgen, addr_type, "r1", input_routes_r3, next_hop=[nh_r3_r1]
654 )
655 assert result is True, "Testcase {} : Failed \n Error {}".format(
656 tc_name, result
657 )
658
659 step("Active-Standby scenario(as-path prepend and Local pref)")
660
661 for addr_type in ADDR_TYPES:
662
663 step("Create prefix-list")
664
665 input_dict_pf = {
666 "r1": {
667 "prefix_lists": {
668 addr_type: {
669 "pf_ls_{}".format(addr_type): [
670 {
671 "seqid": 10,
672 "network": NETWORK3_4[addr_type],
673 "action": "permit",
674 }
675 ]
676 }
677 }
678 }
679 }
680 result = create_prefix_lists(tgen, input_dict_pf)
681 assert result is True, "Testcase {} : Failed \n Error: {}".format(
682 tc_name, result
683 )
684
685 for addr_type in ADDR_TYPES:
686
687 step("Create route-map to match prefix-list and set localpref 500")
688
689 input_dict_rm = {
690 "r1": {
691 "route_maps": {
692 "rmap_PATH1_{}".format(addr_type): [
693 {
694 "action": "permit",
695 "seq_id": 10,
696 "match": {
697 addr_type: {
698 "prefix_lists": "pf_ls_{}".format(addr_type)
699 }
700 },
701 "set": {"locPrf": 500},
702 }
703 ]
704 }
705 }
706 }
707
708 result = create_route_maps(tgen, input_dict_rm)
709 assert result is True, "Testcase {} : Failed \n Error: {}".format(
710 tc_name, result
711 )
712
713 step("Create route-map to match prefix-list and set localpref 600")
714
715 input_dict_rm = {
716 "r1": {
717 "route_maps": {
718 "rmap_PATH2_{}".format(addr_type): [
719 {
720 "action": "permit",
721 "seq_id": 20,
722 "match": {
723 addr_type: {
724 "prefix_lists": "pf_ls_{}".format(addr_type)
725 }
726 },
727 "set": {"locPrf": 600},
728 }
729 ]
730 }
731 }
732 }
733
734 result = create_route_maps(tgen, input_dict_rm)
735 assert result is True, "Testcase {} : Failed \n Error: {}".format(
736 tc_name, result
737 )
738
739 input_dict_rma = {
740 "r1": {
741 "bgp": [
742 {
743 "local_as": "100",
744 "address_family": {
745 addr_type: {
746 "unicast": {
747 "neighbor": {
748 "r3": {
749 "dest_link": {
750 "r1-link1": {
751 "route_maps": [
752 {
753 "name": "rmap_PATH1_{}".format(
754 addr_type
755 ),
756 "direction": "in",
757 }
758 ]
759 }
760 }
761 },
762 "r4": {
763 "dest_link": {
764 "r1-link1": {
765 "route_maps": [
766 {
767 "name": "rmap_PATH2_{}".format(
768 addr_type
769 ),
770 "direction": "in",
771 }
772 ]
773 }
774 }
775 },
776 }
777 }
778 }
779 },
780 }
781 ]
782 }
783 }
784
785 result = create_router_bgp(tgen, topo, input_dict_rma)
786 assert result is True, "Testcase {} : Failed \n Error: {}".format(
787 tc_name, result
788 )
789
790 dut = "r1"
791 attribute = "locPrf"
792
793 for addr_type in ADDR_TYPES:
794
795 step("Verify bestpath is installed as per highest localpref")
796
797 input_routes_r3 = {
798 "r3": {
799 "static_routes": [
800 {"network": [NETWORK3_3[addr_type], NETWORK3_4[addr_type]]}
801 ]
802 }
803 }
804
805 result = verify_best_path_as_per_bgp_attribute(
806 tgen, addr_type, dut, input_routes_r3, attribute
807 )
808 assert result is True, "Testcase {} : Failed \n Error: {}".format(
809 tc_name, result
810 )
811
812 for addr_type in ADDR_TYPES:
813
814 step("Create route-map to match prefix-list and set localpref 700")
815
816 input_dict_rm = {
817 "r1": {
818 "route_maps": {
819 "rmap_PATH1_{}".format(addr_type): [
820 {
821 "action": "permit",
822 "seq_id": 10,
823 "match": {
824 addr_type: {
825 "prefix_lists": "pf_ls_{}".format(addr_type)
826 }
827 },
828 "set": {"locPrf": 700},
829 }
830 ]
831 }
832 }
833 }
834
835 result = create_route_maps(tgen, input_dict_rm)
836 assert result is True, "Testcase {} : Failed \n Error: {}".format(
837 tc_name, result
838 )
839
840 for addr_type in ADDR_TYPES:
841
842 step("Verify bestpath is changed as per highest localpref")
843
844 input_routes_r3 = {
845 "r3": {
846 "static_routes": [
847 {"network": [NETWORK3_3[addr_type], NETWORK3_4[addr_type]]}
848 ]
849 }
850 }
851
852 result = verify_best_path_as_per_bgp_attribute(
853 tgen, addr_type, dut, input_routes_r3, attribute
854 )
855 assert result is True, "Testcase {} : Failed \n Error: {}".format(
856 tc_name, result
857 )
858
859 for addr_type in ADDR_TYPES:
860
861 step("Create route-map to match prefix-list and set as-path prepend")
862
863 input_dict_rm = {
864 "r1": {
865 "route_maps": {
866 "rmap_PATH2_{}".format(addr_type): [
867 {
868 "action": "permit",
869 "seq_id": 20,
870 "match": {
871 addr_type: {
872 "prefix_lists": "pf_ls_{}".format(addr_type)
873 }
874 },
875 "set": {
876 "localpref": 700,
877 "path": {"as_num": "111", "as_action": "prepend"},
878 },
879 }
880 ]
881 }
882 }
883 }
884
885 result = create_route_maps(tgen, input_dict_rm)
886 assert result is True, "Testcase {} : Failed \n Error: {}".format(
887 tc_name, result
888 )
889
890 attribute = "path"
891
892 for addr_type in ADDR_TYPES:
893
894 step("Verify bestpath is changed as per shortest as-path")
895
896 input_routes_r3 = {
897 "r3": {
898 "static_routes": [
899 {"network": [NETWORK3_3[addr_type], NETWORK3_4[addr_type]]}
900 ]
901 }
902 }
903
904 result = verify_best_path_as_per_bgp_attribute(
905 tgen, addr_type, dut, input_routes_r3, attribute
906 )
907 assert result is True, "Testcase {} : Failed \n Error: {}".format(
908 tc_name, result
909 )
910
911 write_test_footer(tc_name)
912
913
914 if __name__ == "__main__":
915 args = ["-s"] + sys.argv[1:]
916 sys.exit(pytest.main(args))