diff --git a/pymisp/api.py b/pymisp/api.py index 2b2c2dbec..90411f3aa 100644 --- a/pymisp/api.py +++ b/pymisp/api.py @@ -17,7 +17,7 @@ from . import __version__, deprecated from .exceptions import PyMISPError, SearchError, NoURL, NoKey, PyMISPEmptyResponse -from .mispevent import MISPEvent, MISPAttribute, MISPUser, MISPOrganisation, MISPSighting, MISPFeed, MISPObject +from .mispevent import MISPEvent, MISPAttribute, MISPUser, MISPOrganisation, MISPSighting, MISPFeed, MISPObject, MISPSharingGroup from .abstract import AbstractMISP, MISPEncode logger = logging.getLogger('pymisp') @@ -2241,6 +2241,20 @@ def cache_all_feeds(self): # ###################### # ### Sharing Groups ### # ###################### + def add_sharing_group(self, name, releasability, description, active=True): + """Add a new sharing group, which includes the organisation associated + with the API key and the local server + + :name: The name of the sharing group to create + :releasability: The releasibility information + :description: The description of the sharing group + :active: Should the sharing group be set to be active? + """ + + new_sg = MISPSharingGroup() + new_sg.from_dict(name=name, releasability=releasability, + description=description, active=active) + return self._rest_add('sharing_groups', new_sg) def sharing_group_org_add(self, sharing_group, organisation, extend=False): '''Add an organisation to a sharing group. @@ -2284,6 +2298,12 @@ def sharing_group_server_remove(self, sharing_group, server): response = self._prepare_request('POST', url, json.dumps(to_jsonify)) return self._check_response(response) + def delete_sharing_group(self, sharing_group): + """Delete a sharing group + :sharing_group: Sharing group's local instance ID, or Sharing group's global uuid + """ + return self._rest_delete("sharing_groups", sharing_group) + # ################### # ### Objects ### # ################### diff --git a/pymisp/mispevent.py b/pymisp/mispevent.py index c660ed41c..3ec8879a2 100644 --- a/pymisp/mispevent.py +++ b/pymisp/mispevent.py @@ -1176,3 +1176,12 @@ def __repr__(self): if hasattr(self, 'name'): return '<{self.__class__.__name__}(name={self.name})'.format(self=self) return '<{self.__class__.__name__}(NotInitialized)'.format(self=self) + + +class MISPSharingGroup(AbstractMISP): + + def __init__(self): + super(MISPSharingGroup, self).__init__() + + def from_dict(self, **kwargs): + super(MISPSharingGroup, self).from_dict(**kwargs) diff --git a/pymisp/tools/openioc.py b/pymisp/tools/openioc.py index 6251b48b4..9d337b152 100755 --- a/pymisp/tools/openioc.py +++ b/pymisp/tools/openioc.py @@ -100,7 +100,7 @@ 'RouteEntryItem/Destination': {'type': 'ip-dst'}, 'RouteEntryItem/Destination/IP': {'type': 'ip-dst', 'comment': 'RouteDestination. '}, - 'RouteEntryItem/Destination/string': {'type': 'url', 'comment': 'RouteDestination. '}, + 'RouteEntryItem/Destination/string': {'type': 'hostname', 'comment': 'RouteDestination. '}, 'ServiceItem/name': {'type': 'windows-service-name'}, @@ -218,7 +218,12 @@ def set_values(value1, value2=None): compositeMapping = '{}|{}'.format(value1.find('context')['search'], value2.find('context')['search']) mapping = get_mapping(compositeMapping, mappingDict=iocMispCompositeMapping) else: - mapping = get_mapping(value1.find('context')['search']) + context_search = value1.find('context')['search'] + content_type = value1.find('content').get('type', None) + if "RouteEntryItem/Destination" in context_search and content_type: + mapping = get_mapping(context_search + '/' + content_type) + else: + mapping = get_mapping(context_search) if mapping: attribute_values.update(mapping)