Skip to content
This repository has been archived by the owner on Aug 18, 2024. It is now read-only.

Groups and roles by permissions #482

Merged
merged 30 commits into from
May 13, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
30 commits
Select commit Hold shift + click to select a range
853ead7
Provide a method to find roles based on permissions.
idimopoulos Apr 25, 2019
566443e
Provide a test for the permission lookup.
idimopoulos Apr 25, 2019
5f6078f
Provide a method to retrieve a user's group list according to a list …
idimopoulos Apr 25, 2019
d436f54
Provide a test for the getGroupsByRoles method.
idimopoulos Apr 25, 2019
5c8449a
Merge remote-tracking branch 'origin/8.x-1.x' into memberships_roles_…
pfrenssen May 7, 2019
53e2755
Adhere to coding standards.
pfrenssen May 7, 2019
2bff25a
Merge branch '8.x-1.x' into memberships_roles_by_permissions
idimopoulos May 7, 2019
8448e9b
Split the method into more methods. Add one helper method and one mor…
idimopoulos May 7, 2019
c121739
Implement the require_all flag functionality.
idimopoulos May 7, 2019
1fdd8f0
Respect legacy ordering of methods.
idimopoulos May 7, 2019
cd54aff
Fix the name and the parameters of the API methods.
idimopoulos May 7, 2019
94831b7
Extend tests to cover multiple cases for the roles and the membership
idimopoulos May 7, 2019
ccd0699
Inlcude a require_all flag in the method.
idimopoulos May 7, 2019
d8d786f
Extend the tests to check for multiple permissions.
idimopoulos May 7, 2019
31c9228
Include more test scenarios to ensure integrity even when more permis…
idimopoulos May 7, 2019
dae4918
Simplify the readability of the check.
idimopoulos May 7, 2019
96e9122
Update documentation.
pfrenssen May 8, 2019
96d8491
Retrieve the service in a 'more proper' way.
idimopoulos May 8, 2019
9ff54bf
Rename variables to avoid ambiguity.
idimopoulos May 8, 2019
1d2b106
Fix almost all of the rest of the nit picks.
idimopoulos May 8, 2019
0c9cdd0
Fix typo of duplicate keyword.
idimopoulos May 8, 2019
5a0326d
Fix the order of the passed arguments.
idimopoulos May 8, 2019
59374cb
Fix calling of method and phpcs errors.
idimopoulos May 9, 2019
0b1b903
Merge remote-tracking branch 'gizra/8.x-1.x' into memberships_roles_b…
pfrenssen May 13, 2019
19b3876
Default to matching on all passed in parameters or roles.
pfrenssen May 13, 2019
ef42f7f
Use PHP 7 return type declarations.
pfrenssen May 13, 2019
0dc1dd5
Move test for a method in OgRoleManager in the relevant test class.
pfrenssen May 13, 2019
a9b04b8
Store the membership manager in a local property instead of repeatedl…
pfrenssen May 13, 2019
cb220c6
Update documentation.
pfrenssen May 13, 2019
3fa48e7
Merge remote-tracking branch 'gizra/8.x-1.x' into memberships_roles_b…
pfrenssen May 13, 2019
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
80 changes: 65 additions & 15 deletions src/MembershipManager.php
Original file line number Diff line number Diff line change
Expand Up @@ -76,13 +76,8 @@ public function getUserGroupIds(AccountInterface $user, array $states = [OgMembe
* {@inheritdoc}
*/
public function getUserGroups(AccountInterface $user, array $states = [OgMembershipInterface::STATE_ACTIVE]) {
$groups = [];

foreach ($this->getUserGroupIds($user, $states) as $entity_type => $entity_ids) {
$groups[$entity_type] = $this->entityTypeManager->getStorage($entity_type)->loadMultiple($entity_ids);
}

return $groups;
$group_ids = $this->getUserGroupIds($user, $states);
return $this->loadGroups($group_ids);
}

/**
Expand Down Expand Up @@ -129,6 +124,36 @@ public function getMembership(EntityInterface $group, AccountInterface $user, ar
return NULL;
}

/**
* {@inheritdoc}
*/
public function getUserGroupIdsByRoles(AccountInterface $user, array $roles, array $states = [OgMembershipInterface::STATE_ACTIVE], bool $require_all_roles = TRUE): array {
$role_ids = array_map(function (OgRoleInterface $role): string {
return $role->id();
}, $roles);

/** @var \Drupal\og\OgMembershipInterface[] $memberships */
$memberships = $this->getMemberships($user, $states);
$memberships = array_filter($memberships, function (OgMembershipInterface $membership) use ($role_ids, $require_all_roles): bool {
$membership_roles_ids = $membership->getRolesIds();
return $require_all_roles ? empty(array_diff($role_ids, $membership_roles_ids)) : !empty(array_intersect($membership_roles_ids, $role_ids));
});

$group_ids = [];
foreach ($memberships as $membership) {
$group_ids[$membership->getGroupEntityType()][] = $membership->getGroupId();
}
return $group_ids;
}

/**
* {@inheritdoc}
*/
public function getUserGroupsByRoles(AccountInterface $user, array $roles, array $states = [OgMembershipInterface::STATE_ACTIVE], bool $require_all_roles = TRUE): array {
$group_ids = $this->getUserGroupIdsByRoles($user, $roles, $states, $require_all_roles);
return $this->loadGroups($group_ids);
}

/**
* {@inheritdoc}
*/
Expand Down Expand Up @@ -299,13 +324,8 @@ public function getGroupIds(EntityInterface $entity, $group_type_id = NULL, $gro
* {@inheritdoc}
*/
public function getGroups(EntityInterface $entity, $group_type_id = NULL, $group_bundle = NULL) {
$groups = [];

foreach ($this->getGroupIds($entity, $group_type_id, $group_bundle) as $entity_type => $entity_ids) {
$groups[$entity_type] = $this->entityTypeManager->getStorage($entity_type)->loadMultiple($entity_ids);
}

return $groups;
$group_ids = $this->getGroupIds($entity, $group_type_id, $group_bundle);
return $this->loadGroups($group_ids);
}

/**
Expand Down Expand Up @@ -413,6 +433,30 @@ protected function prepareConditionArray(array $value, array $default = NULL) {
return array_unique($value);
}

/**
* Loads the entities of an associative array of entity IDs.
*
* @param array[] $group_ids
* An associative array of entity IDs indexed by their entity type ID.
*
* @return \Drupal\Core\Entity\ContentEntityInterface[][]
* An associative array of entities indexed by their entity type ID.
*
* @throws \Drupal\Component\Plugin\Exception\InvalidPluginDefinitionException
* Thrown when the entity type definition of one or more of the passed in
* entity types is invalid.
* @throws \Drupal\Component\Plugin\Exception\PluginNotFoundException
* Thrown when one or more of the passed in entity types is not defined.
*/
protected function loadGroups(array $group_ids): array {
$groups = [];
foreach ($group_ids as $entity_type => $ids) {
$groups[$entity_type] = $this->entityTypeManager->getStorage($entity_type)->loadMultiple($ids);
}

return $groups;
}

/**
* Stores the given list of membership IDs in the static cache backend.
*
Expand All @@ -435,8 +479,14 @@ protected function cacheMembershipIds($cid, array $membership_ids) {
* @param array $ids
* The IDs of the memberships to load.
*
* @return \Drupal\Core\Entity\EntityInterface[]
* @return \Drupal\og\OgMembershipInterface[]
* The membership entities.
*
* @throws \Drupal\Component\Plugin\Exception\InvalidPluginDefinitionException
* Thrown when the entity type definition of one or more of the passed in
* entity types is invalid.
* @throws \Drupal\Component\Plugin\Exception\PluginNotFoundException
* Thrown when one or more of the passed in entity types is not defined.
*/
protected function loadMemberships(array $ids) {
if (empty($ids)) {
Expand Down
44 changes: 42 additions & 2 deletions src/MembershipManagerInterface.php
Original file line number Diff line number Diff line change
Expand Up @@ -43,10 +43,10 @@ public function getUserGroupIds(AccountInterface $user, array $states = [OgMembe
*
* @param \Drupal\Core\Session\AccountInterface $user
* The user to get groups for.
* @param array $states
* @param string[] $states
* (optional) Array with the states to return. Defaults to active.
*
* @return \Drupal\Core\Entity\EntityInterface[][]
* @return \Drupal\Core\Entity\ContentEntityInterface[][]
* An associative array, keyed by group entity type, each item an array of
* group entities.
*
Expand All @@ -55,6 +55,46 @@ public function getUserGroupIds(AccountInterface $user, array $states = [OgMembe
*/
public function getUserGroups(AccountInterface $user, array $states = [OgMembershipInterface::STATE_ACTIVE]);

/**
* Returns an array of groups filtered by the OG roles of the user.
*
* @param \Drupal\Core\Session\AccountInterface $user
* The user to get the groups for.
* @param \Drupal\og\OgRoleInterface[] $roles
* A list of og role objects to filter by.
* @param string[] $states
* (optional) An array of states to filter the memberships by.
* @param bool $require_all_roles
* (optional) If set to TRUE, all requested roles must be present to return
* the group. Set to FALSE to return the groups that match one or more of
* the requested roles. Defaults to TRUE.
*
* @return \Drupal\Core\Entity\ContentEntityInterface[][]
* An associative array, keyed by group entity type, each item an array of
* group entities.
*/
public function getUserGroupsByRoles(AccountInterface $user, array $roles, array $states = [OgMembershipInterface::STATE_ACTIVE], bool $require_all_roles = TRUE): array;

/**
* Returns an array of groups ids filtered by the og roles of the user.
*
* @param \Drupal\Core\Session\AccountInterface $user
* The user to get the groups for.
* @param \Drupal\og\OgRoleInterface[] $roles
* A list of og role objects to filter by.
* @param string[] $states
* (optional) An array of states to filter the memberships by.
* @param bool $require_all_roles
* (optional) If set to TRUE, all requested roles must be present to return
* the group. Set to FALSE to return the groups that match one or more of
* the requested roles. Defaults to TRUE.
*
* @return array[]
* An associative array, keyed by group entity type, each item an array of
* group IDs.
*/
public function getUserGroupIdsByRoles(AccountInterface $user, array $roles, array $states = [OgMembershipInterface::STATE_ACTIVE], bool $require_all_roles = TRUE): array;

/**
* Returns the group memberships a user is associated with.
*
Expand Down
29 changes: 29 additions & 0 deletions src/OgRoleManager.php
Original file line number Diff line number Diff line change
Expand Up @@ -132,6 +132,35 @@ public function getRolesByBundle($entity_type_id, $bundle) {
return $this->ogRoleStorage()->loadByProperties($properties);
}

/**
* {@inheritdoc}
*/
public function getRolesByPermissions(array $permissions, $entity_type_id = NULL, $bundle = NULL, $require_all = TRUE): array {
$role_storage = $this->ogRoleStorage();
$query = $role_storage->getQuery();
if ($require_all) {
// If all permissions are requested, we need to add an AND condition for
// each permission because there is not an easy way to explicitly request
// a subset of an array.
foreach ($permissions as $permission) {
$query->condition('permissions.*', $permission);
}
}
else {
$query->condition('permissions.*', $permissions, 'IN');
}

if (!empty($entity_type_id)) {
$query->condition('group_type', $entity_type_id);
}
if (!empty($bundle)) {
$query->condition('group_bundle', $bundle);
}

$role_ids = $query->execute();
return $role_storage->loadMultiple($role_ids);
}

/**
* {@inheritdoc}
*/
Expand Down
25 changes: 23 additions & 2 deletions src/OgRoleManagerInterface.php
Original file line number Diff line number Diff line change
Expand Up @@ -49,15 +49,36 @@ public function getRequiredDefaultRoles();
* Returns all the roles of a provided group.
*
* @param string $entity_type_id
* The entity type id of the group.
* The entity type ID of the group.
* @param string $bundle
* The bundle of the group.
*
* @return \Drupal\og\OgRoleInterface[]
* An array of roles indexed by their ids.
* An array of roles indexed by their IDs.
*/
public function getRolesByBundle($entity_type_id, $bundle);

/**
* Returns all the roles that have a specific permission.
*
* Optionally filter the roles by entity type ID and bundle.
*
* @param array $permissions
* An array of permissions that the roles must have.
* @param string $entity_type_id
* (optional) The entity type ID of the group.
* @param string $bundle
* (optional) The bundle of the group.
* @param bool $require_all
* (optional) Whether all given permissions are required. When set to FALSE
* all roles that include one or more of the given permissions will be
* returned. Defaults to TRUE.
*
* @return \Drupal\og\OgRoleInterface[]
* An array of roles indexed by their IDs.
*/
public function getRolesByPermissions(array $permissions, $entity_type_id = NULL, $bundle = NULL, $require_all = TRUE): array;

/**
* Deletes the roles associated with a group type.
*
Expand Down
Loading