def update_data(self): """ Update cache. Here we listen to changes in STATE_DB TRANSCEIVER_INFO table and update data only when there is a change (SET, DELETE) """ # This code is not executed in unit test, since mockredis # does not support pubsub if not self.pubsub: redis_client = self.statedb.get_redis_client(self.statedb.STATE_DB) db = self.statedb.get_dbid(self.statedb.STATE_DB) self.pubsub = redis_client.pubsub() self.pubsub.psubscribe("__keyspace@{}__:{}".format( db, self.TRANSCEIVER_KEY_PATTERN)) while True: msg = self.pubsub.get_message() if not msg: break transceiver_entry = msg["channel"].split(b":")[-1].decode() data = msg['data'] # event data # extract interface name interface = transceiver_entry.split( mibs.TABLE_NAME_SEPARATOR_VBAR)[-1] # get interface from interface name ifindex = port_util.get_index_from_str(interface) if ifindex is None: # interface name invalid, skip this entry mibs.logger.warning("Invalid interface name in {} \ in STATE_DB, skipping".format(transceiver_entry)) continue if b"set" in data: self._update_transceiver_cache(interface) elif b"del" in data: # remove deleted transceiver remove_sub_ids = [mibs.get_transceiver_sub_id(ifindex)] # remove all sensor OIDs associated with removed transceiver for sensor in SENSOR_NAME_MAP: remove_sub_ids.append( mibs.get_transceiver_sensor_sub_id(ifindex, sensor)) for sub_id in remove_sub_ids: if sub_id and sub_id in self.physical_entities: self.physical_entities.remove(sub_id)
def _update_transceiver_cache(self, interface): """ Update data for single transceiver :param: interface: Interface name associated with transceiver """ # get interface from interface name ifindex = port_util.get_index_from_str(interface) # update xcvr info from DB # use port's name as key for transceiver info entries sub_id = mibs.get_transceiver_sub_id(ifindex) # add interface to available OID list insort_right(self.physical_entities, sub_id) # get transceiver information from transceiver info entry in STATE DB transceiver_info = Namespace.dbs_get_all( self.statedb, mibs.STATE_DB, mibs.transceiver_info_table(interface)) if not transceiver_info: return # physical class - network port self.physical_classes_map[sub_id] = PhysicalClass.PORT # save values into cache sfp_type, \ self.physical_hw_version_map[sub_id],\ self.physical_serial_number_map[sub_id], \ self.physical_mfg_name_map[sub_id], \ self.physical_model_name_map[sub_id] = get_transceiver_data(transceiver_info) ifalias = self.if_alias_map.get(interface.encode(), b"").decode() # generate a description for this transceiver self.physical_description_map[sub_id] = get_transceiver_description( sfp_type, ifalias) # update transceiver sensor cache self._update_transceiver_sensor_cache(interface)