Skip to content

Commit fa760c4

Browse files
authored
Fix bug: use instance variable instead of class variable in ConfigDBConnector (#99)
And add instance method `serialize_key` using instance variable.
1 parent 6e42d58 commit fa760c4

File tree

1 file changed

+23
-10
lines changed

1 file changed

+23
-10
lines changed

src/swsssdk/configdb.py

Lines changed: 23 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -26,8 +26,6 @@
2626
class ConfigDBConnector(SonicV2Connector):
2727

2828
INIT_INDICATOR = 'CONFIG_DB_INITIALIZED'
29-
TABLE_NAME_SEPARATOR = '|'
30-
KEY_SEPARATOR = '|'
3129

3230
def __init__(self, decode_responses=True, **kwargs):
3331
# By default, connect to Redis through TCP, which does not requires root.
@@ -49,19 +47,26 @@ def __init__(self, decode_responses=True, **kwargs):
4947
'namespace' is implicitly passed to the parent SonicV2Connector class.
5048
"""
5149
super(ConfigDBConnector, self).__init__(**kwargs)
50+
# Trick: to achieve static/instance method "overload", we must use initize the function in ctor
51+
# ref: https://stackoverflow.com/a/28766809/2514803
52+
self.serialize_key = self._serialize_key
53+
self.deserialize_key = self._deserialize_key
54+
55+
self.TABLE_NAME_SEPARATOR = '|'
56+
self.KEY_SEPARATOR = '|'
5257
self.handlers = {}
5358

5459
def __wait_for_db_init(self):
5560
client = self.get_redis_client(self.db_name)
5661
pubsub = client.pubsub()
57-
initialized = client.get(self.INIT_INDICATOR)
62+
initialized = client.get(ConfigDBConnector.INIT_INDICATOR)
5863
if not initialized:
59-
pattern = "__keyspace@{}__:{}".format(self.get_dbid(self.db_name), self.INIT_INDICATOR)
64+
pattern = "__keyspace@{}__:{}".format(self.get_dbid(self.db_name), ConfigDBConnector.INIT_INDICATOR)
6065
pubsub.psubscribe(pattern)
6166
for item in pubsub.listen():
6267
if item['type'] == 'pmessage':
6368
key = item['channel'].split(':', 1)[1]
64-
if key == self.INIT_INDICATOR:
69+
if key == ConfigDBConnector.INIT_INDICATOR:
6570
initialized = client.get(self.INIT_INDICATOR)
6671
if initialized:
6772
break
@@ -151,21 +156,30 @@ def typed_to_raw(self, typed_data):
151156
raw_data[key] = str(value)
152157
return raw_data
153158

159+
# Note: we could not use a class variable for KEY_SEPARATOR, but original dependent code is using
160+
# these static functions. So we implement both static and instance functions with the same name.
161+
# The static function will behave according to ConfigDB separators.
154162
@staticmethod
155-
def serialize_key(key):
163+
def serialize_key(key, separator='|'):
156164
if type(key) is tuple:
157-
return ConfigDBConnector.KEY_SEPARATOR.join(key)
165+
return separator.join(key)
158166
else:
159167
return str(key)
160168

169+
def _serialize_key(self, key):
170+
return ConfigDBConnector.serialize_key(key, self.KEY_SEPARATOR)
171+
161172
@staticmethod
162-
def deserialize_key(key):
163-
tokens = key.split(ConfigDBConnector.KEY_SEPARATOR)
173+
def deserialize_key(key, separator='|'):
174+
tokens = key.split(separator)
164175
if len(tokens) > 1:
165176
return tuple(tokens)
166177
else:
167178
return key
168179

180+
def _deserialize_key(self, key):
181+
return ConfigDBConnector.deserialize_key(key, self.KEY_SEPARATOR)
182+
169183
def set_entry(self, table, key, data):
170184
"""Write a table entry to config db.
171185
Remove extra fields in the db which are not in the data.
@@ -276,7 +290,6 @@ def delete_table(self, table):
276290
client = self.get_redis_client(self.db_name)
277291
pattern = '{}{}*'.format(table.upper(), self.TABLE_NAME_SEPARATOR)
278292
keys = client.keys(pattern)
279-
data = {}
280293
for key in keys:
281294
client.delete(key)
282295

0 commit comments

Comments
 (0)