Changes to object serialization.

stix2.1
Emmanuelle Vargas-Gonzalez 2017-08-15 13:40:47 -04:00
parent e3f82effc7
commit 1b48ad9778
2 changed files with 44 additions and 2 deletions

View File

@ -3,6 +3,7 @@
import collections import collections
import copy import copy
import datetime as dt import datetime as dt
import simplejson as json import simplejson as json
from .exceptions import (AtLeastOnePropertyError, DependentPropertiesError, from .exceptions import (AtLeastOnePropertyError, DependentPropertiesError,
@ -11,7 +12,8 @@ from .exceptions import (AtLeastOnePropertyError, DependentPropertiesError,
MissingPropertiesError, MissingPropertiesError,
MutuallyExclusivePropertiesError, RevokeError, MutuallyExclusivePropertiesError, RevokeError,
UnmodifiablePropertyError) UnmodifiablePropertyError)
from .utils import NOW, format_datetime, get_timestamp, parse_into_datetime from .utils import (NOW, find_property_index, format_datetime, get_timestamp,
parse_into_datetime)
__all__ = ['STIXJSONEncoder', '_STIXBase'] __all__ = ['STIXJSONEncoder', '_STIXBase']
@ -145,9 +147,13 @@ class _STIXBase(collections.Mapping):
def __str__(self): def __str__(self):
properties = self._object_properties() properties = self._object_properties()
def sort_by(element):
return find_property_index(self, properties, element)
# separators kwarg -> don't include spaces after commas. # separators kwarg -> don't include spaces after commas.
return json.dumps(self, indent=4, cls=STIXJSONEncoder, return json.dumps(self, indent=4, cls=STIXJSONEncoder,
item_sort_key=lambda x: properties.index(x[0]), item_sort_key=sort_by,
separators=(",", ": ")) separators=(",", ": "))
def __repr__(self): def __repr__(self):

View File

@ -1,5 +1,7 @@
"""Utility functions and classes for the stix2 library.""" """Utility functions and classes for the stix2 library."""
from stix2 import base
import datetime as dt import datetime as dt
import json import json
@ -115,3 +117,37 @@ def get_dict(data):
return dict(data) return dict(data)
except (ValueError, TypeError): except (ValueError, TypeError):
raise ValueError("Cannot convert '%s' to dictionary." % str(data)) raise ValueError("Cannot convert '%s' to dictionary." % str(data))
def find_property_index(obj, properties, tuple_to_find):
"""Recursively find the property in the object model, return the index
according to the _properties OrderedDict. If its a list look for
individual objects.
"""
try:
if tuple_to_find[1] in obj._inner.values():
return properties.index(tuple_to_find[0])
raise ValueError
except ValueError:
for pv in obj._inner.values():
if isinstance(pv, list):
for item in pv:
if isinstance(item, base._STIXBase):
val = find_property_index(item,
item._object_properties(),
tuple_to_find)
if val is not None:
return val
elif isinstance(pv, dict):
if pv.get(tuple_to_find[0]) is not None:
try:
return int(tuple_to_find[0])
except ValueError:
return len(tuple_to_find[0])
for item in pv.values():
if isinstance(item, base._STIXBase):
val = find_property_index(item,
item._object_properties(),
tuple_to_find)
if val is not None:
return val