Skip to content

Commit 3d34146

Browse files
Martin Roylindycoder
authored andcommitted
Add the vrrp information to the vlan objects
1 parent a688e4e commit 3d34146

File tree

4 files changed

+142
-5
lines changed

4 files changed

+142
-5
lines changed

netman/adapters/switches/juniper/base.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -124,6 +124,7 @@ def get_vlan_from_node(self, vlan_node, config):
124124
vlan.ips = parse_ips(interface_vlan_node)
125125
vlan.access_groups[IN] = parse_inet_filter(interface_vlan_node, "input")
126126
vlan.access_groups[OUT] = parse_inet_filter(interface_vlan_node, "output")
127+
vlan.vrrp_groups = self.custom_strategies.parse_vrrp_groups(interface_vlan_node)
127128
return vlan
128129

129130
def get_interfaces(self):

netman/adapters/switches/juniper/mx.py

Lines changed: 21 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -12,13 +12,14 @@
1212
# See the License for the specific language governing permissions and
1313
# limitations under the License.
1414
from ncclient.xml_ import to_ele, new_ele
15-
from netaddr import IPNetwork
15+
from netaddr import IPAddress, IPNetwork
1616

1717
from netman.adapters.switches.juniper.base import first, Juniper, Update, one_interface, parse_range, to_range, \
1818
first_text
1919
from netman.adapters.switches.juniper.qfx_copper import JuniperQfxCopperCustomStrategies
20-
from netman.core.objects.exceptions import BadVlanName, BadVlanNumber, VlanAlreadyExist, \
21-
UnknownVlan, IPAlreadySet, UnknownIP, AccessVlanNotSet, UnknownInterface, VrrpDoesNotExistForVlan
20+
from netman.core.objects.exceptions import BadVlanName, BadVlanNumber, VlanAlreadyExist, UnknownVlan, IPAlreadySet, \
21+
UnknownIP, AccessVlanNotSet, UnknownInterface, VrrpDoesNotExistForVlan
22+
from netman.core.objects.vrrp_group import VrrpGroup
2223

2324
IRB = "irb"
2425
PREEMPT_HOLD_TIME = 60
@@ -441,6 +442,10 @@ def interface_vlan_members_update(self, name, unit, members_modification):
441442

442443
return content
443444

445+
def parse_vrrp_groups(self, interface_unit):
446+
return [_to_vrrp_group(vrrp_node)
447+
for vrrp_node in interface_unit.xpath("family/inet/address/vrrp-group")]
448+
444449

445450
def one_interface_vlan(vlan_number):
446451
def m():
@@ -482,3 +487,16 @@ def irb_address_update(vlan_number, ip_network, operation=None, children=None):
482487
address.append(child)
483488

484489
return content
490+
491+
492+
def _to_vrrp_group(vrrp_node):
493+
priority = first_text(vrrp_node.xpath("priority"))
494+
track_decrement = first_text(vrrp_node.xpath("track/route/priority-cost"))
495+
496+
return VrrpGroup(
497+
id=int(first_text(vrrp_node.xpath("name"))),
498+
ips=[IPAddress(ip.text) for ip in vrrp_node.xpath("virtual-address")],
499+
priority=int(priority) if priority is not None else None,
500+
track_id=first_text(vrrp_node.xpath("track/route/route_address")),
501+
track_decrement=int(track_decrement) if track_decrement is not None else None,
502+
)

netman/adapters/switches/juniper/standard.py

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -205,3 +205,6 @@ def interface_vlan_members_update(self, name, unit, members_modification):
205205
vlan_node.append(m)
206206

207207
return content
208+
209+
def parse_vrrp_groups(self, interface_unit):
210+
return []

tests/adapters/switches/juniper_mx_test.py

Lines changed: 117 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -15,11 +15,10 @@
1515
import unittest
1616

1717
from flexmock import flexmock, flexmock_teardown
18-
from hamcrest import assert_that, equal_to, instance_of, contains_string, has_length
18+
from hamcrest import assert_that, equal_to, instance_of, contains_string, has_length, is_
1919
from ncclient.operations import RPCError
2020
from ncclient.xml_ import to_ele
2121
from netaddr import IPAddress, IPNetwork
22-
2322
from netman.adapters.switches.juniper.base import Juniper
2423
from netman.adapters.switches.juniper.mx import netconf
2524
from netman.core.objects.access_groups import IN, OUT
@@ -924,6 +923,122 @@ def test_get_vlan_with_interface(self):
924923
assert_that(str(vlan20ip1.ip), equal_to("1.1.1.1"))
925924
assert_that(vlan20ip1.prefixlen, equal_to(24))
926925

926+
def test_get_vlan_with_vrrp(self):
927+
self.switch.in_transaction = False
928+
self.netconf_mock.should_receive("get_config").with_args(source="running", filter=is_xml("""
929+
<filter>
930+
<configuration>
931+
<bridge-domains />
932+
<interfaces />
933+
</configuration>
934+
</filter>
935+
""")).and_return(a_configuration("""
936+
<bridge-domains>
937+
<domain>
938+
<name>WITH-IF</name>
939+
<vlan-id>20</vlan-id>
940+
<routing-interface>irb.20</routing-interface>
941+
</domain>
942+
</bridge-domains>
943+
<interfaces>
944+
<interface>
945+
<name>irb</name>
946+
<unit>
947+
<name>20</name>
948+
<family>
949+
<inet>
950+
<address>
951+
<name>1.1.1.2/24</name>
952+
<vrrp-group>
953+
<name>1</name>
954+
<virtual-address>1.1.1.1</virtual-address>
955+
<priority>90</priority>
956+
<preempt>
957+
<hold-time>60</hold-time>
958+
</preempt>
959+
<accept-data/>
960+
<authentication-type>simple</authentication-type>
961+
<authentication-key>$9$1/aElvwsgoaGz3reKvLX.Pf5n/</authentication-key>
962+
<track>
963+
<route>
964+
<route_address>0.0.0.0/0</route_address>
965+
<routing-instance>default</routing-instance>
966+
<priority-cost>50</priority-cost>
967+
</route>
968+
</track>
969+
</vrrp-group>
970+
</address>
971+
</inet>
972+
</family>
973+
</unit>
974+
</interface>
975+
</interfaces>
976+
"""))
977+
978+
vlan = self.switch.get_vlan(20)
979+
980+
vrrp = vlan.vrrp_groups[0]
981+
assert_that(vrrp.id, is_(1))
982+
assert_that(vrrp.ips, has_length(1))
983+
assert_that(vrrp.ips[0], is_(IPAddress('1.1.1.1')))
984+
assert_that(vrrp.priority, is_(90))
985+
assert_that(vrrp.hello_interval, is_(None))
986+
assert_that(vrrp.dead_interval, is_(None))
987+
assert_that(vrrp.track_id, is_("0.0.0.0/0"))
988+
assert_that(vrrp.track_decrement, is_(50))
989+
990+
def test_get_vlan_with_vrrp_without_optional_fields_and_multiple_vips(self):
991+
self.switch.in_transaction = False
992+
self.netconf_mock.should_receive("get_config").with_args(source="running", filter=is_xml("""
993+
<filter>
994+
<configuration>
995+
<bridge-domains />
996+
<interfaces />
997+
</configuration>
998+
</filter>
999+
""")).and_return(a_configuration("""
1000+
<bridge-domains>
1001+
<domain>
1002+
<name>WITH-IF</name>
1003+
<vlan-id>20</vlan-id>
1004+
<routing-interface>irb.20</routing-interface>
1005+
</domain>
1006+
</bridge-domains>
1007+
<interfaces>
1008+
<interface>
1009+
<name>irb</name>
1010+
<unit>
1011+
<name>20</name>
1012+
<family>
1013+
<inet>
1014+
<address>
1015+
<name>1.1.1.2/24</name>
1016+
<vrrp-group>
1017+
<name>1</name>
1018+
<virtual-address>1.1.1.1</virtual-address>
1019+
<virtual-address>1.1.1.3</virtual-address>
1020+
</vrrp-group>
1021+
</address>
1022+
</inet>
1023+
</family>
1024+
</unit>
1025+
</interface>
1026+
</interfaces>
1027+
"""))
1028+
1029+
vlan = self.switch.get_vlan(20)
1030+
1031+
vrrp = vlan.vrrp_groups[0]
1032+
assert_that(vrrp.id, is_(1))
1033+
assert_that(vrrp.ips, has_length(2))
1034+
assert_that(vrrp.ips[0], is_(IPAddress('1.1.1.1')))
1035+
assert_that(vrrp.ips[1], is_(IPAddress('1.1.1.3')))
1036+
assert_that(vrrp.priority, is_(None))
1037+
assert_that(vrrp.hello_interval, is_(None))
1038+
assert_that(vrrp.dead_interval, is_(None))
1039+
assert_that(vrrp.track_id, is_(None))
1040+
assert_that(vrrp.track_decrement, is_(None))
1041+
9271042
def test_add_vrrp_success(self):
9281043
self.netconf_mock.should_receive("get_config").with_args(source="candidate", filter=is_xml("""
9291044
<filter>

0 commit comments

Comments
 (0)