From 15d738aa775b251941ac3209a42c98499ea3ae73 Mon Sep 17 00:00:00 2001 From: iglocska Date: Fri, 26 Nov 2021 10:51:58 +0100 Subject: [PATCH 01/14] fix: [forms] dropdowns overriding values from request --- templates/element/genericElements/Form/Fields/dropdownField.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/templates/element/genericElements/Form/Fields/dropdownField.php b/templates/element/genericElements/Form/Fields/dropdownField.php index 46b4c81..0bfc0e5 100644 --- a/templates/element/genericElements/Form/Fields/dropdownField.php +++ b/templates/element/genericElements/Form/Fields/dropdownField.php @@ -2,7 +2,7 @@ $controlParams = [ 'options' => $fieldData['options'], 'empty' => $fieldData['empty'] ?? false, - 'value' => $fieldData['value'] ?? [], + 'value' => $fieldData['value'] ?? null, 'multiple' => $fieldData['multiple'] ?? false, 'disabled' => $fieldData['disabled'] ?? false, 'class' => ($fieldData['class'] ?? '') . ' formDropdown form-select' From 2eb2459936382d20f3b2fda70449e9d13cb57533 Mon Sep 17 00:00:00 2001 From: iglocska Date: Fri, 26 Nov 2021 10:52:44 +0100 Subject: [PATCH 02/14] fix: [forms] added missing password form field --- .../element/genericElements/Form/Fields/passwordField.php | 6 ++++++ 1 file changed, 6 insertions(+) create mode 100644 templates/element/genericElements/Form/Fields/passwordField.php diff --git a/templates/element/genericElements/Form/Fields/passwordField.php b/templates/element/genericElements/Form/Fields/passwordField.php new file mode 100644 index 0000000..6831ce6 --- /dev/null +++ b/templates/element/genericElements/Form/Fields/passwordField.php @@ -0,0 +1,6 @@ +FormFieldMassage->prepareFormElement($this->Form, $params, $fieldData); +?> From 2406e31b729d3bf000dddc26f182e80b996fc8ff Mon Sep 17 00:00:00 2001 From: iglocska Date: Fri, 26 Nov 2021 10:53:24 +0100 Subject: [PATCH 03/14] fix: [user add] form fixes --- templates/Users/add.php | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/templates/Users/add.php b/templates/Users/add.php index f215277..a3c90a8 100644 --- a/templates/Users/add.php +++ b/templates/Users/add.php @@ -25,7 +25,8 @@ 'label' => __('Password'), 'type' => 'password', 'required' => $this->request->getParam('action') === 'add' ? 'required' : false, - 'autocomplete' => 'new-password' + 'autocomplete' => 'new-password', + 'value' => '' ], [ 'field' => 'confirm_password', From 7fa0537cfd0577648b75092eea43131589b2485f Mon Sep 17 00:00:00 2001 From: iglocska Date: Sat, 27 Nov 2021 23:51:32 +0100 Subject: [PATCH 04/14] fix: [encryption keys] only show valid options when creating keys as a user --- src/Controller/EncryptionKeysController.php | 16 +++++++++++++--- 1 file changed, 13 insertions(+), 3 deletions(-) diff --git a/src/Controller/EncryptionKeysController.php b/src/Controller/EncryptionKeysController.php index 78bec89..ae2a55b 100644 --- a/src/Controller/EncryptionKeysController.php +++ b/src/Controller/EncryptionKeysController.php @@ -50,16 +50,25 @@ class EncryptionKeysController extends AppController public function add() { $orgConditions = []; + $individualConditions = []; $currentUser = $this->ACL->getUser(); $params = ['redirect' => $this->referer()]; if (empty($currentUser['role']['perm_admin'])) { + $orgConditions = [ + 'id' => $currentUser['organisation_id'] + ]; + if (empty($currentUser['role']['perm_org_admin'])) { + $individualConditions = [ + 'id' => $currentUser['individual_id'] + ]; + } $params['beforeSave'] = function($entity) { if ($entity['owner_model'] === 'organisation') { $entity['owner_id'] = $currentUser['organisation_id']; } else { if ($currentUser['role']['perm_org_admin']) { - $validIndividuals = $this->Organisations->Alignments->find('list', [ - 'fields' => ['distinct(individual_id)'], + $validIndividuals = $this->Organisations->find('list', [ + 'fields' => ['distinct(id)'], 'conditions' => ['organisation_id' => $currentUser['organisation_id']] ]); if (!in_array($entity['owner_id'], $validIndividuals)) { @@ -86,7 +95,8 @@ class EncryptionKeysController extends AppController 'conditions' => $orgConditions ]), 'individual' => $this->Individuals->find('list', [ - 'sort' => ['email' => 'asc'] + 'sort' => ['email' => 'asc'], + 'conditions' => $individualConditions ]) ]; $this->set(compact('dropdownData')); From 22be309dc253c94e2815243a34c14d8a6df97810 Mon Sep 17 00:00:00 2001 From: iglocska Date: Sun, 28 Nov 2021 23:42:22 +0100 Subject: [PATCH 05/14] fix: [ACL] fix wildcard controller checks failing --- src/Controller/Component/ACLComponent.php | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/src/Controller/Component/ACLComponent.php b/src/Controller/Component/ACLComponent.php index cd38752..ea0378f 100644 --- a/src/Controller/Component/ACLComponent.php +++ b/src/Controller/Component/ACLComponent.php @@ -267,9 +267,19 @@ class ACLComponent extends Component return true; } //$this->__checkLoggedActions($user, $controller, $action); + if (isset($this->aclList['*'][$action])) { + if ($this->evaluateAccessLeaf('*', $action)) { + return true; + } + } if (!isset($this->aclList[$controller])) { return $this->__error(404, __('Invalid controller.'), $soft); } + return $this->evaluateAccessLeaf($controller, $action); + } + + private function evaluateAccessLeaf(string $controller, string $action): bool + { if (isset($this->aclList[$controller][$action]) && !empty($this->aclList[$controller][$action])) { if (in_array('*', $this->aclList[$controller][$action])) { return true; From c7d40d42c70728defa37b26ea4c9d1c1c7728092 Mon Sep 17 00:00:00 2001 From: iglocska Date: Mon, 29 Nov 2021 23:37:41 +0100 Subject: [PATCH 06/14] fix: [ACL] added missing entries --- src/Controller/Component/ACLComponent.php | 32 +++++++++++++++++++++-- 1 file changed, 30 insertions(+), 2 deletions(-) diff --git a/src/Controller/Component/ACLComponent.php b/src/Controller/Component/ACLComponent.php index ea0378f..83cd348 100644 --- a/src/Controller/Component/ACLComponent.php +++ b/src/Controller/Component/ACLComponent.php @@ -45,6 +45,9 @@ class ACLComponent extends Component 'index' => ['*'], 'view' => ['*'] ], + 'AuditLogs' => [ + 'index' => ['perm_admin'] + ], 'AuthKeys' => [ 'add' => ['*'], 'delete' => ['*'], @@ -82,19 +85,27 @@ class ACLComponent extends Component 'add' => ['perm_admin'], 'delete' => ['perm_admin'], 'edit' => ['perm_admin'], + 'filtering' => ['*'], 'index' => ['*'], - 'view' => ['*'] + 'tag' => ['perm_tagger'], + 'untag' => ['perm_tagger'], + 'view' => ['*'], + 'viewTags' => ['*'] ], 'Instance' => [ 'home' => ['*'], 'migrate' => ['perm_admin'], 'migrationIndex' => ['perm_admin'], 'rollback' => ['perm_admin'], + 'saveSetting' => ['perm_admin'], + 'searchAll' => ['*'], + 'settings' => ['perm_admin'], 'status' => ['*'] ], 'LocalTools' => [ 'action' => ['perm_admin'], 'add' => ['perm_admin'], + 'batchAction' => ['perm_admin'], 'broodTools' => ['perm_admin'], 'connectionRequest' => ['perm_admin'], 'connectLocal' => ['perm_admin'], @@ -123,7 +134,10 @@ class ACLComponent extends Component 'edit' => ['perm_admin'], 'filtering' => ['*'], 'index' => ['*'], - 'view' => ['*'] + 'tag' => ['perm_tagger'], + 'untag' => ['perm_tagger'], + 'view' => ['*'], + 'viewTags' => ['*'] ], 'Outbox' => [ 'createEntry' => ['perm_admin'], @@ -162,8 +176,22 @@ class ACLComponent extends Component 'login' => ['*'], 'logout' => ['*'], 'register' => ['*'], + 'settings' => ['*'], 'toggle' => ['perm_org_admin'], 'view' => ['*'] + ], + 'UserSettings' => [ + 'index' => ['*'], + 'view' => ['*'], + 'add' => ['*'], + 'edit' => ['*'], + 'delete' => ['*'], + 'getSettingByName' => ['*'], + 'setSetting' => ['*'], + 'saveSetting' => ['*'], + 'getBookmarks' => ['*'], + 'saveBookmark' => ['*'], + 'deleteBookmark' => ['*'] ] ); From 392faa60e48205319c873a11535f343f1d938193 Mon Sep 17 00:00:00 2001 From: iglocska Date: Tue, 30 Nov 2021 00:00:05 +0100 Subject: [PATCH 07/14] new: [ACL] getRoleAccess endpoint added - prints all valid URLs for the current user's role --- src/Controller/AppController.php | 5 ++ src/Controller/Component/ACLComponent.php | 70 ++++++++++++----------- 2 files changed, 43 insertions(+), 32 deletions(-) diff --git a/src/Controller/AppController.php b/src/Controller/AppController.php index 7afab70..2b0102a 100644 --- a/src/Controller/AppController.php +++ b/src/Controller/AppController.php @@ -188,4 +188,9 @@ class AppController extends Controller { return $this->RestResponse->viewData($this->ACL->findMissingFunctionNames()); } + + public function getRoleAccess() + { + return $this->RestResponse->viewData($this->ACL->getRoleAccess()); + } } diff --git a/src/Controller/Component/ACLComponent.php b/src/Controller/Component/ACLComponent.php index 83cd348..cac1bc0 100644 --- a/src/Controller/Component/ACLComponent.php +++ b/src/Controller/Component/ACLComponent.php @@ -435,13 +435,19 @@ class ACLComponent extends Component return $missing; } + public function getRoleAccess($role = false) + { + $urls = $this->__checkRoleAccess($role); + return $urls; + } + public function printRoleAccess($content = false) { $results = []; - $this->Role = TableRegistry::get('Role'); + $this->Role = TableRegistry::get('Roles'); $conditions = []; if (is_numeric($content)) { - $conditions = array('Role.id' => $content); + $conditions = array('id' => $content); } $roles = $this->Role->find('all', array( 'recursive' => -1, @@ -457,40 +463,40 @@ class ACLComponent extends Component return $results; } - private function __checkRoleAccess($role) + private function __checkRoleAccess($role = false) { $result = []; - foreach ($this->__aclList as $controller => $actions) { - $controllerNames = Inflector::variable($controller) == Inflector::underscore($controller) ? array(Inflector::variable($controller)) : array(Inflector::variable($controller), Inflector::underscore($controller)); - foreach ($controllerNames as $controllerName) { - foreach ($actions as $action => $permissions) { - if ($role['perm_site_admin']) { - $result[] = DS . $controllerName . DS . $action; - } elseif (in_array('*', $permissions)) { - $result[] = DS . $controllerName . DS . $action . DS . '*'; - } elseif (isset($permissions['OR'])) { - $access = false; - foreach ($permissions['OR'] as $permission) { - if ($role[$permission]) { - $access = true; - } + if ($role === false) { + $role = $this->getUser()['role']; + } + foreach ($this->aclList as $controller => $actions) { + foreach ($actions as $action => $permissions) { + if ($role['perm_admin']) { + $result[] = DS . $controller . DS . $action; + } elseif (in_array('*', $permissions)) { + $result[] = DS . $controller . DS . $action . DS . '*'; + } elseif (isset($permissions['OR'])) { + $access = false; + foreach ($permissions['OR'] as $permission) { + if ($role[$permission]) { + $access = true; } - if ($access) { - $result[] = DS . $controllerName . DS . $action . DS . '*'; - } - } elseif (isset($permissions['AND'])) { - $access = true; - foreach ($permissions['AND'] as $permission) { - if ($role[$permission]) { - $access = false; - } - } - if ($access) { - $result[] = DS . $controllerName . DS . $action . DS . '*'; - } - } elseif (isset($permissions[0]) && $role[$permissions[0]]) { - $result[] = DS . $controllerName . DS . $action . DS . '*'; } + if ($access) { + $result[] = DS . $controller . DS . $action . DS . '*'; + } + } elseif (isset($permissions['AND'])) { + $access = true; + foreach ($permissions['AND'] as $permission) { + if ($role[$permission]) { + $access = false; + } + } + if ($access) { + $result[] = DS . $controller . DS . $action . DS . '*'; + } + } elseif (isset($permissions[0]) && $role[$permissions[0]]) { + $result[] = DS . $controller . DS . $action . DS . '*'; } } } From fbb1a52724663eda3350d5ac3484b0c314647057 Mon Sep 17 00:00:00 2001 From: iglocska Date: Wed, 1 Dec 2021 14:22:02 +0100 Subject: [PATCH 08/14] new: [ACL component] new functionalities - getRoleAccess now returns either URLs or arrays - array format allows for easy checking of controller + action pairs --- src/Controller/Component/ACLComponent.php | 32 +++++++++++++++-------- 1 file changed, 21 insertions(+), 11 deletions(-) diff --git a/src/Controller/Component/ACLComponent.php b/src/Controller/Component/ACLComponent.php index cac1bc0..afa70ff 100644 --- a/src/Controller/Component/ACLComponent.php +++ b/src/Controller/Component/ACLComponent.php @@ -37,6 +37,7 @@ class ACLComponent extends Component '*' => [ 'checkPermission' => ['*'], 'generateUUID' => ['*'], + 'getRoleAccess' => ['*'], 'queryACL' => ['perm_admin'] ], 'Alignments' => [ @@ -435,10 +436,9 @@ class ACLComponent extends Component return $missing; } - public function getRoleAccess($role = false) + public function getRoleAccess($role = false, $url_mode = true) { - $urls = $this->__checkRoleAccess($role); - return $urls; + return $this->__checkRoleAccess($role, $url_mode); } public function printRoleAccess($content = false) @@ -463,18 +463,28 @@ class ACLComponent extends Component return $results; } - private function __checkRoleAccess($role = false) + private function __formatControllerAction(array $results, string $controller, string $action, $url_mode = true): array { - $result = []; + if ($url_mode) { + $results[] = DS . $controller . DS . $action . DS . '*'; + } else { + $results[$controller][] = $action; + } + return $results; + } + + private function __checkRoleAccess($role = false, $url_mode = true) + { + $results = []; if ($role === false) { $role = $this->getUser()['role']; } foreach ($this->aclList as $controller => $actions) { foreach ($actions as $action => $permissions) { if ($role['perm_admin']) { - $result[] = DS . $controller . DS . $action; + $results = $this->__formatControllerAction($results, $controller, $action, $url_mode); } elseif (in_array('*', $permissions)) { - $result[] = DS . $controller . DS . $action . DS . '*'; + $results = $this->__formatControllerAction($results, $controller, $action, $url_mode); } elseif (isset($permissions['OR'])) { $access = false; foreach ($permissions['OR'] as $permission) { @@ -483,7 +493,7 @@ class ACLComponent extends Component } } if ($access) { - $result[] = DS . $controller . DS . $action . DS . '*'; + $results = $this->__formatControllerAction($results, $controller, $action, $url_mode); } } elseif (isset($permissions['AND'])) { $access = true; @@ -493,14 +503,14 @@ class ACLComponent extends Component } } if ($access) { - $result[] = DS . $controller . DS . $action . DS . '*'; + $results = $this->__formatControllerAction($results, $controller, $action, $url_mode); } } elseif (isset($permissions[0]) && $role[$permissions[0]]) { - $result[] = DS . $controller . DS . $action . DS . '*'; + $results = $this->__formatControllerAction($results, $controller, $action, $url_mode); } } } - return $result; + return $results; } public function getMenu() From e408f29a0552e0f2fbda7d84e8253b941a512bc2 Mon Sep 17 00:00:00 2001 From: iglocska Date: Wed, 1 Dec 2021 14:23:27 +0100 Subject: [PATCH 09/14] chg: [appcontroller] minor changes - getRoleAccess now returns array format - moved setting of view variables behind a rest check, to avoid additional unused actions for API queries - current user's role access matrix passed to view via "roleAccess" --- src/Controller/AppController.php | 27 +++++++++++++++------------ 1 file changed, 15 insertions(+), 12 deletions(-) diff --git a/src/Controller/AppController.php b/src/Controller/AppController.php index 2b0102a..4d41bac 100644 --- a/src/Controller/AppController.php +++ b/src/Controller/AppController.php @@ -116,6 +116,7 @@ class AppController extends Controller if (!$this->ParamHandler->isRest()) { $this->set('menu', $this->ACL->getMenu()); $this->set('loggedUser', $this->ACL->getUser()); + $this->set('roleAccess', $this->ACL->getRoleAccess(false, false)); } } else if ($this->ParamHandler->isRest()) { throw new MethodNotAllowedException(__('Invalid user credentials.')); @@ -131,18 +132,20 @@ class AppController extends Controller } $this->ACL->checkAccess(); - $this->set('breadcrumb', $this->Navigation->getBreadcrumb()); - $this->set('ajax', $this->request->is('ajax')); - $this->request->getParam('prefix'); - $this->set('baseurl', Configure::read('App.fullBaseUrl')); - if (!empty($user) && !empty($user->user_settings_by_name['ui.bsTheme']['value'])) { - $this->set('bsTheme', $user->user_settings_by_name['ui.bsTheme']['value']); - } else { - $this->set('bsTheme', Configure::check('ui.bsTheme') ? Configure::read('ui.bsTheme') : 'default'); - } + if (!$this->ParamHandler->isRest()) { + $this->set('breadcrumb', $this->Navigation->getBreadcrumb()); + $this->set('ajax', $this->request->is('ajax')); + $this->request->getParam('prefix'); + $this->set('baseurl', Configure::read('App.fullBaseUrl')); + if (!empty($user) && !empty($user->user_settings_by_name['ui.bsTheme']['value'])) { + $this->set('bsTheme', $user->user_settings_by_name['ui.bsTheme']['value']); + } else { + $this->set('bsTheme', Configure::check('ui.bsTheme') ? Configure::read('ui.bsTheme') : 'default'); + } - if ($this->modelClass == 'Tags.Tags') { - $this->set('metaGroup', !empty($this->isAdmin) ? 'Administration' : 'Cerebrate'); + if ($this->modelClass == 'Tags.Tags') { + $this->set('metaGroup', !empty($this->isAdmin) ? 'Administration' : 'Cerebrate'); + } } } @@ -191,6 +194,6 @@ class AppController extends Controller public function getRoleAccess() { - return $this->RestResponse->viewData($this->ACL->getRoleAccess()); + return $this->RestResponse->viewData($this->ACL->getRoleAccess(false, false)); } } From 1e31f4d1dd8cf22784421ca455b362bfe9c85314 Mon Sep 17 00:00:00 2001 From: iglocska Date: Wed, 1 Dec 2021 14:25:34 +0100 Subject: [PATCH 10/14] new: [ACL Helper] check access for controller / action pair for given user - accesible everywhere in the UI --- src/View/AppView.php | 1 + src/View/Helper/ACLHelper.php | 25 +++++++++++++++++++++++++ 2 files changed, 26 insertions(+) create mode 100644 src/View/Helper/ACLHelper.php diff --git a/src/View/AppView.php b/src/View/AppView.php index 7636a87..9018168 100644 --- a/src/View/AppView.php +++ b/src/View/AppView.php @@ -44,5 +44,6 @@ class AppView extends View $this->loadHelper('FormFieldMassage'); $this->loadHelper('Paginator', ['templates' => 'cerebrate-pagination-templates']); $this->loadHelper('Tags.Tag'); + $this->loadHelper('ACL'); } } diff --git a/src/View/Helper/ACLHelper.php b/src/View/Helper/ACLHelper.php new file mode 100644 index 0000000..e563e82 --- /dev/null +++ b/src/View/Helper/ACLHelper.php @@ -0,0 +1,25 @@ +roleAccess)) { + $this->roleAccess = $this->getView()->get('roleAccess'); + } + if ( + in_array($action, $this->roleAccess['*']) || + (isset($this->roleAccess[$controller]) && in_array($action, $this->roleAccess[$controller])) + ) { + return true; + } else { + return false; + } + } +} From 332f374e01965cc9c44389de381f8d15866535ca Mon Sep 17 00:00:00 2001 From: iglocska Date: Wed, 1 Dec 2021 14:26:20 +0100 Subject: [PATCH 11/14] chg: [sharing group index] add button now has the new checkaccess conditions applied --- templates/SharingGroups/index.php | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/templates/SharingGroups/index.php b/templates/SharingGroups/index.php index 2aae744..96315e6 100644 --- a/templates/SharingGroups/index.php +++ b/templates/SharingGroups/index.php @@ -10,7 +10,8 @@ echo $this->element('genericElements/IndexTable/index_table', [ 'data' => [ 'type' => 'simple', 'text' => __('Add sharing group'), - 'popover_url' => '/SharingGroups/add' + 'popover_url' => '/SharingGroups/add', + 'requirement' => $this->ACL->checkAccess('SharingGroups', 'add') ] ] ], From 4c7dc85d0e8a67a3fe0fcff6f2a7d2ef629b7ebe Mon Sep 17 00:00:00 2001 From: iglocska Date: Wed, 1 Dec 2021 15:24:08 +0100 Subject: [PATCH 12/14] fix: [encryptions] fixed adding encryption keys --- src/Controller/EncryptionKeysController.php | 13 ++++++++----- 1 file changed, 8 insertions(+), 5 deletions(-) diff --git a/src/Controller/EncryptionKeysController.php b/src/Controller/EncryptionKeysController.php index ae2a55b..bafe8ce 100644 --- a/src/Controller/EncryptionKeysController.php +++ b/src/Controller/EncryptionKeysController.php @@ -62,16 +62,18 @@ class EncryptionKeysController extends AppController 'id' => $currentUser['individual_id'] ]; } - $params['beforeSave'] = function($entity) { + $params['beforeSave'] = function($entity) use($currentUser) { if ($entity['owner_model'] === 'organisation') { $entity['owner_id'] = $currentUser['organisation_id']; } else { if ($currentUser['role']['perm_org_admin']) { - $validIndividuals = $this->Organisations->find('list', [ - 'fields' => ['distinct(id)'], + $this->loadModel('Alignments'); + $validIndividuals = $this->Alignments->find('list', [ + 'keyField' => 'individual_id', + 'valueField' => 'id', 'conditions' => ['organisation_id' => $currentUser['organisation_id']] - ]); - if (!in_array($entity['owner_id'], $validIndividuals)) { + ])->toArray(); + if (!isset($validIndividuals[$entity['owner_id']])) { throw new MethodNotAllowedException(__('Selected individual cannot be linked by the current user.')); } } else { @@ -80,6 +82,7 @@ class EncryptionKeysController extends AppController } } } + return $entity; }; } $this->CRUD->add($params); From 5041a57e08dc8cfc41d0d680c19d5c8b1c9a1d5f Mon Sep 17 00:00:00 2001 From: iglocska Date: Sat, 4 Dec 2021 23:58:42 +0100 Subject: [PATCH 13/14] fix: [sharing groups] index members column fixed --- templates/SharingGroups/index.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/templates/SharingGroups/index.php b/templates/SharingGroups/index.php index 96315e6..946d19a 100644 --- a/templates/SharingGroups/index.php +++ b/templates/SharingGroups/index.php @@ -49,7 +49,7 @@ echo $this->element('genericElements/IndexTable/index_table', [ ], [ 'name' => __('Members'), - 'data_path' => 'alignments', + 'data_path' => 'sharing_group_orgs', 'element' => 'count_summary', 'url' => '/sharingGroups/view/{{id}}', 'url_data_path' => 'id' From bb3b264cfbed3e6e5b941cc276860579bbe950d7 Mon Sep 17 00:00:00 2001 From: iglocska Date: Sun, 5 Dec 2021 00:02:33 +0100 Subject: [PATCH 14/14] fix: [sharing group index] fixed members link --- templates/SharingGroups/index.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/templates/SharingGroups/index.php b/templates/SharingGroups/index.php index 946d19a..c930bed 100644 --- a/templates/SharingGroups/index.php +++ b/templates/SharingGroups/index.php @@ -51,7 +51,7 @@ echo $this->element('genericElements/IndexTable/index_table', [ 'name' => __('Members'), 'data_path' => 'sharing_group_orgs', 'element' => 'count_summary', - 'url' => '/sharingGroups/view/{{id}}', + 'url' => '/sharingGroups/view/{{url_data}}', 'url_data_path' => 'id' ] ],