From: Coleman Watts Date: Thu, 7 Jan 2016 20:59:42 +0000 (-0500) Subject: CRM-17795 - Add basic permission checks for api joins X-Git-Url: https://vcs.fsf.org/?a=commitdiff_plain;h=a762b3809afbc737cc7a447ed78376cfad152ed4;p=civicrm-core.git CRM-17795 - Add basic permission checks for api joins --- diff --git a/Civi/API/SelectQuery.php b/Civi/API/SelectQuery.php index d9879eeccb..ca054b4db6 100644 --- a/Civi/API/SelectQuery.php +++ b/Civi/API/SelectQuery.php @@ -341,6 +341,10 @@ class SelectQuery { if (!isset($fkField['FKApiName']) && !isset($fkField['FKClassName'])) { return NULL; } + // Ensure we have permission to access the other api + if (!$this->checkPermissionToJoin($fkField['FKApiName'], array_slice($stack, 0, $depth))) { + return NULL; + } if (!isset($fkField['FKApiSpec'])) { $fkField['FKApiSpec'] = \_civicrm_api_get_fields($fkField['FKApiName']); } @@ -411,4 +415,38 @@ class SelectQuery { return NULL; } + /** + * Check permission to join onto another api entity + * + * @param string $entity + * @param array $fieldStack + * The stack of fields leading up to this join + * @return bool + */ + private function checkPermissionToJoin($entity, $fieldStack) { + if (empty($this->params['check_permissions'])) { + return TRUE; + } + // Build an array of params that relate to the joined entity + $params = array( + 'version' => 3, + 'return' => array(), + 'check_permissions' => \CRM_Utils_Array::value('check_permissions', $this->params, FALSE), + ); + $prefix = implode('.', $fieldStack) . '.'; + $len = strlen($prefix); + foreach ($this->options['return'] as $key => $ret) { + if (strpos($key, $prefix) === 0) { + $params['return'][substr($key, $len)] = $ret; + } + } + foreach ($this->params as $key => $param) { + if (strpos($key, $prefix) === 0) { + $params[substr($key, $len)] = $param; + } + } + + return \Civi::service('civi_api_kernel')->runAuthorize($entity, 'get', $params); + } + }