From 7402e1b3b6e5826965ee03a4c73df57035d86aba Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Rapha=C3=ABl=20Vinot?= Date: Thu, 29 Aug 2019 18:08:53 +0200 Subject: [PATCH] new: Initial support for communities --- pymisp/aping.py | 35 ++++++++++++++++++++++++++++++++- pymisp/mispevent.py | 14 +++++++++++++ tests/testlive_comprehensive.py | 6 ++++++ 3 files changed, 54 insertions(+), 1 deletion(-) diff --git a/pymisp/aping.py b/pymisp/aping.py index 8c8fe53..b9c446b 100644 --- a/pymisp/aping.py +++ b/pymisp/aping.py @@ -18,7 +18,7 @@ import sys from . import __version__ from .exceptions import MISPServerError, PyMISPUnexpectedResponse, PyMISPNotImplementedYet, PyMISPError, NoURL, NoKey from .api import everything_broken, PyMISP -from .mispevent import MISPEvent, MISPAttribute, MISPSighting, MISPLog, MISPObject, MISPUser, MISPOrganisation, MISPShadowAttribute, MISPWarninglist, MISPTaxonomy, MISPGalaxy, MISPNoticelist, MISPObjectReference, MISPObjectTemplate, MISPSharingGroup, MISPRole, MISPServer, MISPFeed, MISPEventDelegation +from .mispevent import MISPEvent, MISPAttribute, MISPSighting, MISPLog, MISPObject, MISPUser, MISPOrganisation, MISPShadowAttribute, MISPWarninglist, MISPTaxonomy, MISPGalaxy, MISPNoticelist, MISPObjectReference, MISPObjectTemplate, MISPSharingGroup, MISPRole, MISPServer, MISPFeed, MISPEventDelegation, MISPCommunity from .abstract import MISPEncode, MISPTag, AbstractMISP SearchType = TypeVar('SearchType', str, int) @@ -1714,6 +1714,39 @@ class ExpandedPyMISP(PyMISP): # ## END Search methods ### + # ## BEGIN Communities ### + + def communities(self, pythonify: bool=False): + """Get all the communities.""" + communities = self._prepare_request('GET', 'communities') + communities = self._check_response(communities, expect_json=True) + if not (self.global_pythonify or pythonify) or 'errors' in communities: + return communities + to_return = [] + for community in communities: + c = MISPCommunity() + c.from_dict(**community) + to_return.append(c) + return to_return + + def get_community(self, community: Union[MISPCommunity, int, str, UUID], pythonify: bool=False): + '''Get an community from a MISP instance''' + community_id = self.__get_uuid_or_id_from_abstract_misp(community) + community = self._prepare_request('GET', f'communities/view/{community_id}') + community = self._check_response(community, expect_json=True) + if not (self.global_pythonify or pythonify) or 'errors' in community: + return community + c = MISPCommunity() + c.from_dict(**community) + return c + + def request_community_access(self, community: Union[MISPCommunity, int, str, UUID], sync: bool=False, + requestor_org_description: str='', requestor_email_user: str='', + message: str='', anonymise: bool=False): + pass + + # ## END Communities ### + # ## BEGIN Event Delegation ### def event_delegations(self, pythonify: bool=False): diff --git a/pymisp/mispevent.py b/pymisp/mispevent.py index 2f1df47..15a3550 100644 --- a/pymisp/mispevent.py +++ b/pymisp/mispevent.py @@ -1105,6 +1105,20 @@ class MISPShadowAttribute(AbstractMISP): return '<{self.__class__.__name__}(NotInitialized)'.format(self=self) +class MISPCommunity(AbstractMISP): + + def __init__(self): + super(MISPCommunity, self).__init__() + + def from_dict(self, **kwargs): + if kwargs.get('Community'): + kwargs = kwargs.get('Community') + super(MISPCommunity, self).from_dict(**kwargs) + + def __repr__(self): + return '<{self.__class__.__name__}(name={self.name}, uuid={self.uuid})'.format(self=self) + + class MISPObject(AbstractMISP): def __init__(self, name, strict=False, standalone=False, default_attributes_parameters={}, **kwargs): diff --git a/tests/testlive_comprehensive.py b/tests/testlive_comprehensive.py index 8b95609..333bf97 100644 --- a/tests/testlive_comprehensive.py +++ b/tests/testlive_comprehensive.py @@ -1924,6 +1924,12 @@ class TestComprehensive(unittest.TestCase): # Delete event self.admin_misp_connector.delete_event(first) + def test_communities(self): + communities = self.admin_misp_connector.communities(pythonify=True) + self.assertEqual(communities[0].name, 'CIRCL Private Sector Information Sharing Community - aka MISPPRIV') + community = self.admin_misp_connector.get_community(communities[1], pythonify=True) + self.assertEqual(community.name, 'CIRCL n/g CSIRT information sharing community - aka MISP') + def test_upload_stix(self): # FIXME https://github.com/MISP/MISP/issues/4892 pass