Merge pull request #203 from oasis-open/200-filter-contains

Add "contains" filter
stix2.0
Greg Back 2018-07-05 15:47:09 -05:00 committed by GitHub
commit 49c1931b4b
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 32 additions and 2 deletions

View File

@ -369,6 +369,7 @@
"* < \n",
"* ```>=```\n",
"* <=\n",
"* contains\n",
"\n",
"Value types of the property values must be one of these (Python) types:\n",
"\n",

View File

@ -9,7 +9,7 @@ from datetime import datetime
from stix2.utils import format_datetime
"""Supported filter operations"""
FILTER_OPS = ['=', '!=', 'in', '>', '<', '>=', '<=']
FILTER_OPS = ['=', '!=', 'in', '>', '<', '>=', '<=', 'contains']
"""Supported filter value types"""
FILTER_VALUE_TYPES = [bool, dict, float, int, list, str, tuple]
@ -100,6 +100,11 @@ class Filter(collections.namedtuple("Filter", ['property', 'op', 'value'])):
return stix_obj_property != self.value
elif self.op == "in":
return stix_obj_property in self.value
elif self.op == "contains":
if isinstance(self.value, dict):
return self.value in stix_obj_property.values()
else:
return self.value in stix_obj_property
elif self.op == ">":
return stix_obj_property > self.value
elif self.op == "<":

View File

@ -100,7 +100,9 @@ filters = [
Filter("object_marking_refs", "=", "marking-definition--613f2e26-0000-4000-8000-b8e91df99dc9"),
Filter("granular_markings.selectors", "in", "description"),
Filter("external_references.source_name", "=", "CVE"),
Filter("objects", "=", {"0": {"type": "file", "name": "HAL 9000.exe"}})
Filter("objects", "=", {"0": {"type": "file", "name": "HAL 9000.exe"}}),
Filter("objects", "contains", {"type": "file", "name": "HAL 9000.exe"}),
Filter("labels", "contains", "heartbleed"),
]
# same as above objects but converted to real Python STIX2 objects
@ -302,6 +304,28 @@ def test_apply_common_filters13():
assert len(resp) == 1
def test_apply_common_filters14():
# Return any object that contains a specific File Cyber Observable Object
resp = list(apply_common_filters(stix_objs, [filters[15]]))
assert resp[0]['id'] == stix_objs[4]['id']
assert len(resp) == 1
resp = list(apply_common_filters(real_stix_objs, [filters[15]]))
assert resp[0].id == real_stix_objs[4].id
assert len(resp) == 1
def test_apply_common_filters15():
# Return any object that contains 'heartbleed' in "labels"
resp = list(apply_common_filters(stix_objs, [filters[16]]))
assert resp[0]['id'] == stix_objs[3]['id']
assert len(resp) == 1
resp = list(apply_common_filters(real_stix_objs, [filters[16]]))
assert resp[0].id == real_stix_objs[3].id
assert len(resp) == 1
def test_datetime_filter_behavior():
"""if a filter is initialized with its value being a datetime object
OR the STIX object property being filtered on is a datetime object, all