Fix notify filter when data item is None
When data[k] is None during match check, we are getting annoying TypeError exceptions like: "TypeError: expected string or buffer". This patch adds a check that data[k] is something the regex can do matching. Change-Id: I75c8f602a59a90aeb5a6973f2e9e25708194ad78
This commit is contained in:
parent
fcf114294b
commit
3cdfe15897
@ -15,6 +15,8 @@
|
|||||||
|
|
||||||
import re
|
import re
|
||||||
|
|
||||||
|
import six
|
||||||
|
|
||||||
|
|
||||||
class NotificationFilter(object):
|
class NotificationFilter(object):
|
||||||
|
|
||||||
@ -31,7 +33,7 @@ class NotificationFilter(object):
|
|||||||
filter_rule = NotificationFilter(
|
filter_rule = NotificationFilter(
|
||||||
publisher_id='^compute.*',
|
publisher_id='^compute.*',
|
||||||
context={'tenant_id': '^5f643cfc-664b-4c69-8000-ce2ed7b08216$',
|
context={'tenant_id': '^5f643cfc-664b-4c69-8000-ce2ed7b08216$',
|
||||||
'roles='private'},
|
'roles': 'private'},
|
||||||
event_type='^compute\.instance\..*',
|
event_type='^compute\.instance\..*',
|
||||||
metadata={'timestamp': 'Aug'},
|
metadata={'timestamp': 'Aug'},
|
||||||
payload={'state': '^active$')
|
payload={'state': '^active$')
|
||||||
@ -58,15 +60,27 @@ class NotificationFilter(object):
|
|||||||
return dict((k, re.compile(regex_list[k])) for k in regex_list)
|
return dict((k, re.compile(regex_list[k])) for k in regex_list)
|
||||||
|
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def _check_for_mismatch(data, regex):
|
def _check_for_single_mismatch(data, regex):
|
||||||
if isinstance(regex, dict):
|
if regex is None:
|
||||||
for k in regex:
|
return False
|
||||||
if (k not in data or not regex[k].match(data[k])):
|
if not isinstance(data, six.string_types):
|
||||||
return True
|
return True
|
||||||
elif regex is not None and not regex.match(data):
|
if not regex.match(data):
|
||||||
return True
|
return True
|
||||||
return False
|
return False
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def _check_for_mismatch(cls, data, regex):
|
||||||
|
if isinstance(regex, dict):
|
||||||
|
for k in regex:
|
||||||
|
if k not in data:
|
||||||
|
return True
|
||||||
|
if cls._check_for_single_mismatch(data[k], regex[k]):
|
||||||
|
return True
|
||||||
|
return False
|
||||||
|
else:
|
||||||
|
return cls._check_for_single_mismatch(data, regex)
|
||||||
|
|
||||||
def match(self, context, publisher_id, event_type, metadata, payload):
|
def match(self, context, publisher_id, event_type, metadata, payload):
|
||||||
if (self._check_for_mismatch(publisher_id, self._regex_publisher_id) or
|
if (self._check_for_mismatch(publisher_id, self._regex_publisher_id) or
|
||||||
self._check_for_mismatch(event_type, self._regex_event_type) or
|
self._check_for_mismatch(event_type, self._regex_event_type) or
|
||||||
|
@ -163,6 +163,13 @@ class TestDispatcherFilter(test_utils.BaseTestCase):
|
|||||||
event_type='instance.create.start',
|
event_type='instance.create.start',
|
||||||
context={},
|
context={},
|
||||||
match=False)),
|
match=False)),
|
||||||
|
# this is only for simulation
|
||||||
|
('event_type_not_string',
|
||||||
|
dict(filter_rule=dict(event_type='^instance\.delete'),
|
||||||
|
publisher_id='compute01.manager',
|
||||||
|
event_type=['instance.swim', 'instance.fly'],
|
||||||
|
context={},
|
||||||
|
match=False)),
|
||||||
('context_match',
|
('context_match',
|
||||||
dict(filter_rule=dict(context={'user': '^adm'}),
|
dict(filter_rule=dict(context={'user': '^adm'}),
|
||||||
publisher_id='compute01.manager',
|
publisher_id='compute01.manager',
|
||||||
@ -206,6 +213,12 @@ class TestDispatcherFilter(test_utils.BaseTestCase):
|
|||||||
event_type='instance.create.start',
|
event_type='instance.create.start',
|
||||||
context={},
|
context={},
|
||||||
match=False)),
|
match=False)),
|
||||||
|
('payload_value_none',
|
||||||
|
dict(filter_rule=dict(payload={'virtual_size': '2048'}),
|
||||||
|
publisher_id='compute01.manager',
|
||||||
|
event_type='instance.create.start',
|
||||||
|
context={},
|
||||||
|
match=False)),
|
||||||
('mix_match',
|
('mix_match',
|
||||||
dict(filter_rule=dict(event_type='^instance\.create',
|
dict(filter_rule=dict(event_type='^instance\.create',
|
||||||
publisher_id='^compute',
|
publisher_id='^compute',
|
||||||
@ -214,7 +227,6 @@ class TestDispatcherFilter(test_utils.BaseTestCase):
|
|||||||
event_type='instance.create.start',
|
event_type='instance.create.start',
|
||||||
context={'user': 'admin'},
|
context={'user': 'admin'},
|
||||||
match=True)),
|
match=True)),
|
||||||
|
|
||||||
]
|
]
|
||||||
|
|
||||||
def test_filters(self):
|
def test_filters(self):
|
||||||
@ -224,7 +236,7 @@ class TestDispatcherFilter(test_utils.BaseTestCase):
|
|||||||
|
|
||||||
dispatcher = notify_dispatcher.NotificationDispatcher(
|
dispatcher = notify_dispatcher.NotificationDispatcher(
|
||||||
[endpoint], serializer=None)
|
[endpoint], serializer=None)
|
||||||
message = {'payload': {'state': 'active'},
|
message = {'payload': {'state': 'active', 'virtual_size': None},
|
||||||
'priority': 'info',
|
'priority': 'info',
|
||||||
'publisher_id': self.publisher_id,
|
'publisher_id': self.publisher_id,
|
||||||
'event_type': self.event_type,
|
'event_type': self.event_type,
|
||||||
|
Loading…
Reference in New Issue
Block a user