From e4abd639d5c20505621e4508c1344b1fcbe5d23b Mon Sep 17 00:00:00 2001 From: Sami Mokaddem Date: Tue, 4 Oct 2022 16:27:50 +0200 Subject: [PATCH] new: [galaxyCluster:restSearch] Allow filtering by elements --- .../Component/RestResponseComponent.php | 8 ++++- app/Model/GalaxyCluster.php | 7 +++- app/Model/GalaxyElement.php | 33 +++++++++++++++++++ 3 files changed, 46 insertions(+), 2 deletions(-) diff --git a/app/Controller/Component/RestResponseComponent.php b/app/Controller/Component/RestResponseComponent.php index 340d84340..162cc886c 100644 --- a/app/Controller/Component/RestResponseComponent.php +++ b/app/Controller/Component/RestResponseComponent.php @@ -155,7 +155,7 @@ class RestResponseComponent extends Component ), 'restSearch' => array( 'description' => "Search MISP using a list of filter parameters and return the data in the selected format. This API allows pagination via the page and limit parameters.", - 'optional' => array('page', 'limit', 'id', 'uuid', 'galaxy_id', 'galaxy_uuid', 'version', 'distribution', 'org_id', 'orgc_id', 'tag_name', 'custom', 'minimal', 'published', 'value', 'extends_uuid'), + 'optional' => array('page', 'limit', 'id', 'uuid', 'galaxy_id', 'galaxy_uuid', 'version', 'distribution', 'org_id', 'orgc_id', 'tag_name', 'custom', 'minimal', 'published', 'value', 'elements', 'extends_uuid'), 'params' => array() ), ), @@ -1035,6 +1035,12 @@ class RestResponseComponent extends Component 'operators' => ['equal', 'not_equal'], 'values' => array(0 => 'dist1'), ), + 'elements' => array( + 'input' => 'text', + 'type' => 'string', + 'operators' => array('equal'), + 'help' => __('Allow providing a JSON containing the keys and values to search for. Example: {"synonyms": "apt42"}'), + ), 'email' => array( 'input' => 'text', 'type' => 'string', diff --git a/app/Model/GalaxyCluster.php b/app/Model/GalaxyCluster.php index 3587f8221..f9758c182 100644 --- a/app/Model/GalaxyCluster.php +++ b/app/Model/GalaxyCluster.php @@ -1325,8 +1325,13 @@ class GalaxyCluster extends AppModel } } + if (isset($filters['elements'])) { + $matchingIDs = $this->GalaxyElement->getClusterIDsFromMatchingElements($user, $filters['elements']); + $filters['id'] = $matchingIDs; + } + $simpleParams = array( - 'uuid', 'galaxy_id', 'version', 'distribution', 'type', 'value', 'default', 'extends_uuid', 'tag_name', 'published' + 'uuid', 'galaxy_id', 'version', 'distribution', 'type', 'value', 'default', 'extends_uuid', 'tag_name', 'published', 'id', ); foreach ($simpleParams as $k => $simpleParam) { if (isset($filters[$simpleParam])) { diff --git a/app/Model/GalaxyElement.php b/app/Model/GalaxyElement.php index d2a4ad5ab..dd3a6fd04 100644 --- a/app/Model/GalaxyElement.php +++ b/app/Model/GalaxyElement.php @@ -130,4 +130,37 @@ class GalaxyElement extends AppModel $expanded = Hash::expand($keyedValue); return $expanded; } + + /** + * getClusterIDsFromMatchingElements + * + * @param array $user + * @param array $elements an associative array containg the elements to search for + * Example: {"synonyms": "apt42"} + * @return array + */ + public function getClusterIDsFromMatchingElements(array $user, array $elements): array + { + $elementConditions = []; + foreach ($elements as $key => $value) { + $elementConditions[] = [ + 'GalaxyElement.key' => $key, + 'GalaxyElement.value' => $value, + ]; + } + $conditions = [ + $this->buildACLConditions($user), + $elementConditions, + ]; + $elements = $this->find('all', [ + 'conditions' => $conditions, + 'contain' => ['GalaxyCluster' => ['fields' => ['id', 'distribution', 'org_id']]], + 'recursive' => -1 + ]); + $clusterIDs = []; + foreach ($elements as $element) { + $clusterIDs[] = $element['GalaxyElement']['galaxy_cluster_id']; + } + return $clusterIDs; + } }