diff --git a/config-templates/perun_attributes.php b/config-templates/perun_attributes.php index 45ddfba384b67a4392015764375829753027285b..6a8a00da600162d207dca962ac7fc320b124b582 100644 --- a/config-templates/perun_attributes.php +++ b/config-templates/perun_attributes.php @@ -252,6 +252,11 @@ $config = [ 'ldap' => 'capabilities', 'type' => 'array', ], + 'perunResourceAttribute_MFAEnforced' => [ + 'rpc' => 'urn:perun:resource:attribute-def:def:proxyMFAEnforced', + 'ldap' => 'proxyMFAEnforced', + 'type' => 'bool', + ], /* * ENTITYLESS ATTRIBUTES diff --git a/lib/AdapterLdap.php b/lib/AdapterLdap.php index 7b923d46b4e73fe6fcb27dacd26917e562c3aa7a..5b095d8a97a778354cf4ee3014a825a34474338e 100644 --- a/lib/AdapterLdap.php +++ b/lib/AdapterLdap.php @@ -743,4 +743,87 @@ class AdapterLdap extends Adapter return array_values(array_unique($facilityCapabilities[self::CAPABILITIES])); } + + public function getResourceAttributeValues( + string $spEntityId, + string $entityIdAttr, + int $userId, + array $attributeNames + ): array { + if (empty($spEntityId)) { + Logger::warning( + self::DEBUG_PREFIX . + 'getResourceAttributeValues - empty spEntityId provided, returning empty array.' + ); + return []; + } + + $facility = $this->getFacilityByEntityId($spEntityId, $entityIdAttr); + if ($facility === null || $facility->getId() === null) { + Logger::warning( + self::DEBUG_PREFIX . sprintf( + 'getResourceAttributeValues - no facility (or facility with null ID) found for EntityID \'%s\',' + . 'returning empty array.', + $spEntityId + ) + ); + return []; + } + + $resources = $this->connector->searchForEntities( + $this->ldapBase, + '(&(objectClass=perunResource)(perunFacilityDn=perunFacilityId=' . $facility->getId() . ',' + . $this->ldapBase . '))', + ['perunResourceId', self::ASSIGNED_GROUP_ID] + $attributeNames + ); + if (empty($resources)) { + Logger::debug( + self::DEBUG_PREFIX . sprintf( + 'getResourceAttributeValues - no resources found for SP with EntityID \'%s\',' + . ' returning empty array.', + $spEntityId + ) + ); + return []; + } + + $userGroups = $this->getUsersGroupsOnFacility($spEntityId, $userId, $entityIdAttr); + $userGroupsIds = []; + foreach ($userGroups as $userGroup) { + if ($userGroup === null || $userGroup->getId() === null) { + Logger::debug( + self::DEBUG_PREFIX . + 'getResourceAttributeValues - skipping user group due to null group or null group ID.' + ); + continue; + } + $userGroupsIds[] = $userGroup->getId(); + } + + $result = []; + foreach ($resources as $resource) { + if (($resource[self::ASSIGNED_GROUP_ID] ?? null) === null) { + Logger::debug( + self::DEBUG_PREFIX . + 'getResourceAttributeValues - skipping resource due to null resource or null assigned group ID.' + ); + continue; + } + foreach ($resource[self::ASSIGNED_GROUP_ID] as $groupId) { + if (in_array($groupId, $userGroupsIds, true)) { + $result[$resource['perunResourceId'][0]] = []; + foreach ($attributeNames as $attributeName) { + if (!empty($resource[$attributeName])) { + $result[$resource['perunResourceId'][0]][$attributeName] = array_merge( + $result[$resource['perunResourceId'][0]][$attributeName] ?? [], + $resource[$attributeName] + ); + } + } + break; + } + } + } + return $result; + } } diff --git a/lib/AdapterRpc.php b/lib/AdapterRpc.php index 679bd2b6a4c1d6a3efb730ddffffb872beae60b6..64670c6ca0b63a40a881a55113ca0345713db03d 100644 --- a/lib/AdapterRpc.php +++ b/lib/AdapterRpc.php @@ -901,6 +901,71 @@ class AdapterRpc extends Adapter ); } + public function getResourceAttributeValues( + string $spEntityId, + string $entityIdAttr, + int $userId, + array $attributeNames + ): array { + $facility = $this->getFacilityByEntityId($spEntityId, $entityIdAttr); + if ($facility === null || $facility->getId() === null) { + Logger::warning( + self::DEBUG_PREFIX . sprintf( + 'getResourceAttributeValues - no facility (or facility with null ID) found for EntityID \'%s\',' + . ' returning empty array.', + $spEntityId + ) + ); + return []; + } + + $userResources = $this->connector->get( + 'UsersManager', + 'getAllowedResources', + ['user' => $userId, 'facility' => $facility->getId()] + ); + if (empty($userResources)) { + Logger::debug( + self::DEBUG_PREFIX . sprintf( + 'getResourceAttributeValues - no resources with user access found for SP with EntityID \'%s\',' + . ' returning empty array.', + $spEntityId + ) + ); + return []; + } + + $result = []; + foreach ($userResources as $resource) { + if ($resource === null || $resource->getId() === null) { + Logger::debug( + self::DEBUG_PREFIX . + 'getResourceAttributeValues - skipping resource due to null resource or null resource ID.' + ); + continue; + } + $resourceId = $resource->getId(); + + $resourceAttributes = $this->connector->get('attributesManager', 'getAttributes', [ + 'resource' => $resourceId, + 'attrNames' => $attributeNames + ]); + foreach ($resourceAttributes as $resourceAttribute) { + $attributeName = $resourceAttribute['friendlyName']; + if (empty($resourceAttribute['value'])) { + Logger::debug( + self::DEBUG_PREFIX . 'getResourceAttributeValues - skipping attribute' . + $attributeName . 'due to empty(or false) value.' + ); + continue; + } + + $result[$resourceId][$attributeName][] = $resourceAttribute['value']; + } + } + return $result; + } + private function getAttributes($perunAttrs, $attrNamesMap) { $attributes = [];