Skip to content

Commit b3e7f1c

Browse files
preetham-singhisabelmsft
authored andcommitted
Fixes #12170: Delete subinterface and recreate the subinterface in (sonic-net#2513)
* Fixes #12170: Delete subinterface and recreate the subinterface in default-vrf while unbinding subinterface from user defined vrf.
1 parent 44c5d1c commit b3e7f1c

File tree

2 files changed

+55
-10
lines changed

2 files changed

+55
-10
lines changed

config/main.py

+16
Original file line numberDiff line numberDiff line change
@@ -5148,6 +5148,22 @@ def unbind(ctx, interface_name):
51485148
for ipaddress in interface_ipaddresses:
51495149
remove_router_interface_ip_address(config_db, interface_name, ipaddress)
51505150
if table_name == "VLAN_SUB_INTERFACE":
5151+
# First delete subinterface, once subinterface deletion successful,
5152+
# recreate same with same config on default vrf
5153+
if 'state_db' not in ctx.obj:
5154+
if ctx.obj['namespace'] is DEFAULT_NAMESPACE:
5155+
state_db = SonicV2Connector(use_unix_socket_path=True)
5156+
else:
5157+
state_db = SonicV2Connector(use_unix_socket_path=True, namespace=ctx.obj['namespace'])
5158+
state_db.connect(state_db.STATE_DB, False)
5159+
else:
5160+
state_db = ctx.obj['state_db']
5161+
5162+
config_db.set_entry(table_name, interface_name, None)
5163+
_hash = '{}{}'.format('INTERFACE_TABLE|', interface_name)
5164+
while state_db.exists(state_db.STATE_DB, _hash):
5165+
time.sleep(0.01)
5166+
state_db.close(state_db.STATE_DB)
51515167
config_db.set_entry(table_name, interface_name, subintf_entry)
51525168
else:
51535169
config_db.set_entry(table_name, interface_name, None)

tests/vrf_test.py

+39-10
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,9 @@
66

77
import config.main as config
88
import show.main as show
9+
import threading
910

11+
DEFAULT_NAMESPACE = ''
1012
test_path = os.path.dirname(os.path.abspath(__file__))
1113
mock_db_path = os.path.join(test_path, "vrf_input")
1214

@@ -16,6 +18,11 @@ def setup_class(cls):
1618
print("SETUP")
1719
os.environ["UTILITIES_UNIT_TESTING"] = "1"
1820

21+
def update_statedb(self, db, db_name, key):
22+
import time
23+
time.sleep(0.5)
24+
db.delete(db_name, key)
25+
1926
def test_vrf_show(self):
2027
from .mock_tables import dbconnector
2128
jsonfile_config = os.path.join(mock_db_path, "config_db")
@@ -64,59 +71,81 @@ def test_vrf_bind_unbind(self):
6471
assert result.exit_code == 0
6572
assert result.output == expected_output
6673

67-
obj = {'config_db':db.cfgdb}
74+
75+
vrf_obj = {'config_db':db.cfgdb, 'namespace':db.db.namespace}
6876

6977
expected_output_unbind = "Interface Ethernet4 IP disabled and address(es) removed due to unbinding VRF.\n"
70-
result = runner.invoke(config.config.commands["interface"].commands["vrf"].commands["unbind"], ["Ethernet4"], obj=obj)
78+
result = runner.invoke(config.config.commands["interface"].commands["vrf"].commands["unbind"], ["Ethernet4"], obj=vrf_obj)
79+
7180
print(result.exit_code, result.output)
7281
assert result.exit_code == 0
7382
assert 'Ethernet4' not in db.cfgdb.get_table('INTERFACE')
7483
assert result.output == expected_output_unbind
7584

7685
expected_output_unbind = "Interface Loopback0 IP disabled and address(es) removed due to unbinding VRF.\n"
77-
result = runner.invoke(config.config.commands["interface"].commands["vrf"].commands["unbind"], ["Loopback0"], obj=obj)
86+
87+
result = runner.invoke(config.config.commands["interface"].commands["vrf"].commands["unbind"], ["Loopback0"], obj=vrf_obj)
88+
7889
print(result.exit_code, result.output)
7990
assert result.exit_code == 0
8091
assert 'Loopback0' not in db.cfgdb.get_table('LOOPBACK_INTERFACE')
8192
assert result.output == expected_output_unbind
8293

8394
expected_output_unbind = "Interface Vlan40 IP disabled and address(es) removed due to unbinding VRF.\n"
84-
result = runner.invoke(config.config.commands["interface"].commands["vrf"].commands["unbind"], ["Vlan40"], obj=obj)
95+
96+
result = runner.invoke(config.config.commands["interface"].commands["vrf"].commands["unbind"], ["Vlan40"], obj=vrf_obj)
97+
8598
print(result.exit_code, result.output)
8699
assert result.exit_code == 0
87100
assert 'Vlan40' not in db.cfgdb.get_table('VLAN_INTERFACE')
88101
assert result.output == expected_output_unbind
89102

90103
expected_output_unbind = "Interface PortChannel0002 IP disabled and address(es) removed due to unbinding VRF.\n"
91-
result = runner.invoke(config.config.commands["interface"].commands["vrf"].commands["unbind"], ["PortChannel0002"], obj=obj)
104+
105+
result = runner.invoke(config.config.commands["interface"].commands["vrf"].commands["unbind"], ["PortChannel0002"], obj=vrf_obj)
106+
92107
print(result.exit_code, result.output)
93108
assert result.exit_code == 0
94109
assert 'PortChannel002' not in db.cfgdb.get_table('PORTCHANNEL_INTERFACE')
95110
assert result.output == expected_output_unbind
96111

112+
vrf_obj = {'config_db':db.cfgdb, 'namespace':DEFAULT_NAMESPACE}
113+
state_db = SonicV2Connector(use_unix_socket_path=True, namespace='')
114+
state_db.connect(state_db.STATE_DB, False)
115+
_hash = "INTERFACE_TABLE|Eth36.10"
116+
state_db.set(db.db.STATE_DB, _hash, "state", "ok")
117+
vrf_obj['state_db'] = state_db
118+
97119
expected_output_unbind = "Interface Eth36.10 IP disabled and address(es) removed due to unbinding VRF.\n"
98-
result = runner.invoke(config.config.commands["interface"].commands["vrf"].commands["unbind"], ["Eth36.10"], obj=obj)
120+
T1 = threading.Thread( target = self.update_statedb, args = (state_db, db.db.STATE_DB, _hash))
121+
T1.start()
122+
result = runner.invoke(config.config.commands["interface"].commands["vrf"].commands["unbind"], ["Eth36.10"], obj=vrf_obj)
123+
T1.join()
99124
print(result.exit_code, result.output)
100125
assert result.exit_code == 0
101126
assert ('vrf_name', 'Vrf102') not in db.cfgdb.get_table('VLAN_SUB_INTERFACE')['Eth36.10']
102127
assert result.output == expected_output_unbind
103128

129+
vrf_obj = {'config_db':db.cfgdb, 'namespace':DEFAULT_NAMESPACE}
130+
104131
expected_output_unbind = "Interface Ethernet0.10 IP disabled and address(es) removed due to unbinding VRF.\n"
105-
result = runner.invoke(config.config.commands["interface"].commands["vrf"].commands["unbind"], ["Ethernet0.10"], obj=obj)
132+
133+
result = runner.invoke(config.config.commands["interface"].commands["vrf"].commands["unbind"], ["Ethernet0.10"], obj=vrf_obj)
134+
106135
print(result.exit_code, result.output)
107136
assert result.exit_code == 0
108137
assert ('vrf_name', 'Vrf101') not in db.cfgdb.get_table('VLAN_SUB_INTERFACE')['Ethernet0.10']
109138
assert result.output == expected_output_unbind
110139

111140
expected_output_unbind = "Interface Po0002.101 IP disabled and address(es) removed due to unbinding VRF.\n"
112-
result = runner.invoke(config.config.commands["interface"].commands["vrf"].commands["unbind"], ["Po0002.101"], obj=obj)
141+
142+
result = runner.invoke(config.config.commands["interface"].commands["vrf"].commands["unbind"], ["Po0002.101"], obj=vrf_obj)
143+
113144
print(result.exit_code, result.output)
114145
assert result.exit_code == 0
115146
assert ('vrf_name', 'Vrf103') not in db.cfgdb.get_table('VLAN_SUB_INTERFACE')['Po0002.101']
116147
assert result.output == expected_output_unbind
117148

118-
vrf_obj = {'config_db':db.cfgdb, 'namespace':db.db.namespace}
119-
120149
expected_output_bind = "Interface Ethernet0 IP disabled and address(es) removed due to binding VRF Vrf1.\n"
121150
result = runner.invoke(config.config.commands["interface"].commands["vrf"].commands["bind"], ["Ethernet0", "Vrf1"], obj=vrf_obj)
122151
assert result.exit_code == 0

0 commit comments

Comments
 (0)