Extend object serialization options for _STIXBase
parent
8c2af813b2
commit
d6c14139f3
|
@ -153,15 +153,7 @@ class _STIXBase(collections.Mapping):
|
|||
super(_STIXBase, self).__setattr__(name, value)
|
||||
|
||||
def __str__(self):
|
||||
properties = self.object_properties()
|
||||
|
||||
def sort_by(element):
|
||||
return find_property_index(self, properties, element)
|
||||
|
||||
# separators kwarg -> don't include spaces after commas.
|
||||
return json.dumps(self, indent=4, cls=STIXJSONEncoder,
|
||||
item_sort_key=sort_by,
|
||||
separators=(",", ": "))
|
||||
return self.serialize(pretty=True)
|
||||
|
||||
def __repr__(self):
|
||||
props = [(k, self[k]) for k in self.object_properties() if self.get(k)]
|
||||
|
@ -185,6 +177,38 @@ class _STIXBase(collections.Mapping):
|
|||
def revoke(self):
|
||||
return _revoke(self)
|
||||
|
||||
def serialize(self, pretty=False, **kwargs):
|
||||
"""
|
||||
Serialize a STIX object.
|
||||
|
||||
Args:
|
||||
pretty (bool): If True, output properties following the STIX specs
|
||||
formatting. This includes indentation. Refer to notes for more
|
||||
details.
|
||||
**kwargs: The arguments for a json.dumps() call.
|
||||
|
||||
Returns:
|
||||
dict: The serialized JSON object.
|
||||
|
||||
Note:
|
||||
The argument ``pretty=True`` will output the STIX object following
|
||||
spec order. Using this argument greatly impacts object serialization
|
||||
performance. If your use case is centered across machine-to-machine
|
||||
operation it is recommended to set ``pretty=False``.
|
||||
|
||||
When ``pretty=True`` the following key-value pairs will be added or
|
||||
overridden: indent=4, separators=(",", ": "), item_sort_key=sort_by.
|
||||
"""
|
||||
if pretty:
|
||||
properties = self.object_properties()
|
||||
|
||||
def sort_by(element):
|
||||
return find_property_index(self, properties, element)
|
||||
|
||||
kwargs.update({'indent': 4, 'separators': (",", ": "), 'item_sort_key': sort_by})
|
||||
|
||||
return json.dumps(self, cls=STIXJSONEncoder, **kwargs)
|
||||
|
||||
|
||||
class _Observable(_STIXBase):
|
||||
|
||||
|
|
|
@ -1,8 +1,9 @@
|
|||
import json
|
||||
|
||||
import pytest
|
||||
|
||||
import stix2
|
||||
|
||||
|
||||
EXPECTED_BUNDLE = """{
|
||||
"type": "bundle",
|
||||
"id": "bundle--00000000-0000-0000-0000-000000000004",
|
||||
|
@ -41,6 +42,44 @@ EXPECTED_BUNDLE = """{
|
|||
]
|
||||
}"""
|
||||
|
||||
EXPECTED_BUNDLE_DICT = {
|
||||
"type": "bundle",
|
||||
"id": "bundle--00000000-0000-0000-0000-000000000004",
|
||||
"spec_version": "2.0",
|
||||
"objects": [
|
||||
{
|
||||
"type": "indicator",
|
||||
"id": "indicator--00000000-0000-0000-0000-000000000001",
|
||||
"created": "2017-01-01T12:34:56.000Z",
|
||||
"modified": "2017-01-01T12:34:56.000Z",
|
||||
"pattern": "[file:hashes.MD5 = 'd41d8cd98f00b204e9800998ecf8427e']",
|
||||
"valid_from": "2017-01-01T12:34:56Z",
|
||||
"labels": [
|
||||
"malicious-activity"
|
||||
]
|
||||
},
|
||||
{
|
||||
"type": "malware",
|
||||
"id": "malware--00000000-0000-0000-0000-000000000002",
|
||||
"created": "2017-01-01T12:34:56.000Z",
|
||||
"modified": "2017-01-01T12:34:56.000Z",
|
||||
"name": "Cryptolocker",
|
||||
"labels": [
|
||||
"ransomware"
|
||||
]
|
||||
},
|
||||
{
|
||||
"type": "relationship",
|
||||
"id": "relationship--00000000-0000-0000-0000-000000000003",
|
||||
"created": "2017-01-01T12:34:56.000Z",
|
||||
"modified": "2017-01-01T12:34:56.000Z",
|
||||
"relationship_type": "indicates",
|
||||
"source_ref": "indicator--01234567-89ab-cdef-0123-456789abcdef",
|
||||
"target_ref": "malware--fedcba98-7654-3210-fedc-ba9876543210"
|
||||
}
|
||||
]
|
||||
}
|
||||
|
||||
|
||||
def test_empty_bundle():
|
||||
bundle = stix2.Bundle()
|
||||
|
@ -82,10 +121,18 @@ def test_bundle_with_wrong_spec_version():
|
|||
assert str(excinfo.value) == "Invalid value for Bundle 'spec_version': must equal '2.0'."
|
||||
|
||||
|
||||
def test_create_bundle(indicator, malware, relationship):
|
||||
def test_create_bundle1(indicator, malware, relationship):
|
||||
bundle = stix2.Bundle(objects=[indicator, malware, relationship])
|
||||
|
||||
assert str(bundle) == EXPECTED_BUNDLE
|
||||
assert bundle.serialize(pretty=True) == EXPECTED_BUNDLE
|
||||
|
||||
|
||||
def test_create_bundle2(indicator, malware, relationship):
|
||||
bundle = stix2.Bundle(objects=[indicator, malware, relationship])
|
||||
|
||||
print(repr(bundle))
|
||||
assert json.loads(bundle.serialize()) == EXPECTED_BUNDLE_DICT
|
||||
|
||||
|
||||
def test_create_bundle_with_positional_args(indicator, malware, relationship):
|
||||
|
|
Loading…
Reference in New Issue