class Listener(object):
# pylint: disable=too-many-instance-attributes
def __init__(self):
- NotificationQueue.register(self.log_type1, 'type1', priority=90)
- NotificationQueue.register(self.log_type2, 'type2')
- NotificationQueue.register(self.log_type1_3, ['type1', 'type3'])
- NotificationQueue.register(self.log_all, priority=50)
self.type1 = []
self.type1_ts = []
self.type2 = []
self.all = []
self.all_ts = []
+ def register(self):
+ NotificationQueue.register(self.log_type1, 'type1', priority=90)
+ NotificationQueue.register(self.log_type2, 'type2')
+ NotificationQueue.register(self.log_type1_3, ['type1', 'type3'])
+ NotificationQueue.register(self.log_all, priority=50)
+
# these should be ignored by the queue
NotificationQueue.register(self.log_type1, 'type1')
NotificationQueue.register(self.log_type1_3, ['type1', 'type3'])
self.type1_3_ts = []
self.all = []
self.all_ts = []
+ NotificationQueue.deregister(self.log_type1, 'type1')
+ NotificationQueue.deregister(self.log_type2, 'type2')
+ NotificationQueue.deregister(self.log_type1_3, ['type1', 'type3'])
+ NotificationQueue.deregister(self.log_all)
class NotificationQueueTest(unittest.TestCase):
cls.listener = Listener()
def setUp(self):
+ self.listener.register()
+
+ def tearDown(self):
self.listener.clear()
def test_invalid_register(self):
self.assertEqual(len(self.listener.type2), 200)
self.assertEqual(len(self.listener.type1_3), 400)
self.assertEqual(len(self.listener.all), 600)
+
+ def test_deregister(self):
+ NotificationQueue.start_queue()
+ NotificationQueue.new_notification('type1', 1)
+ NotificationQueue.new_notification('type3', 3)
+ NotificationQueue.stop()
+ self.assertEqual(self.listener.type1, [1])
+ self.assertEqual(self.listener.type1_3, [1, 3])
+
+ NotificationQueue.start_queue()
+ NotificationQueue.deregister(self.listener.log_type1_3, ['type1'])
+ NotificationQueue.new_notification('type1', 4)
+ NotificationQueue.new_notification('type3', 5)
+ NotificationQueue.stop()
+ self.assertEqual(self.listener.type1, [1, 4])
+ self.assertEqual(self.listener.type1_3, [1, 3, 5])
"""
with cls._lock:
if not n_types:
- if not cls._registered_handler(func, cls._ALL_TYPES_):
- cls._listeners[cls._ALL_TYPES_].add((priority, func))
- return
- if isinstance(n_types, str):
- if not cls._registered_handler(func, n_types):
- cls._listeners[n_types].add((priority, func))
- elif isinstance(n_types, list):
- for typ in n_types:
- if not cls._registered_handler(func, typ):
- cls._listeners[typ].add((priority, func))
- else:
+ n_types = [cls._ALL_TYPES_]
+ elif isinstance(n_types, str):
+ n_types = [n_types]
+ elif not isinstance(n_types, list):
+ raise Exception("n_types param is neither a string nor a list")
+ for ev_type in n_types:
+ if not cls._registered_handler(func, ev_type):
+ cls._listeners[ev_type].add((priority, func))
+ logger.debug("NQ: function %s was registered for events of"
+ " type %s", func, ev_type)
+
+ @classmethod
+ def deregister(cls, func, n_types=None):
+ """Removes the listener function from this notification queue
+
+ If the second parameter `n_types` is ommitted, the function is removed
+ from all event types, otherwise the function is removed only for the
+ specified event types.
+
+ Args:
+ func (function): python function
+ n_types (str|list): the single event type, or a list of event types
+ """
+ with cls._lock:
+ if not n_types:
+ n_types = list(cls._listeners.keys())
+ elif isinstance(n_types, str):
+ n_types = [n_types]
+ elif not isinstance(n_types, list):
raise Exception("n_types param is neither a string nor a list")
+ for ev_type in n_types:
+ listeners = cls._listeners[ev_type]
+ toRemove = None
+ for pr, fn in listeners:
+ if fn == func:
+ toRemove = (pr, fn)
+ break
+ if toRemove:
+ listeners.discard(toRemove)
+ logger.debug("NQ: function %s was deregistered for events "
+ "of type %s", func, ev_type)
@classmethod
def new_notification(cls, notify_type, notify_value):