Completed
Push — master ( a3cce1...d6fbcc )
by Marcel
09:39
created

AttributeValueProvider   A

Complexity

Total Complexity 14

Size/Duplication

Total Lines 134
Duplicated Lines 0 %

Test Coverage

Coverage 10.34%

Importance

Changes 3
Bugs 0 Features 0
Metric Value
eloc 55
c 3
b 0
f 0
dl 0
loc 134
ccs 6
cts 58
cp 0.1034
rs 10
wmc 14

7 Methods

Rating   Name   Duplication   Size   Complexity  
A getUserAttributeValues() 0 6 1
A getRequestedAttributes() 0 5 1
A getValuesForUser() 0 20 4
A getCommonAttributesForUser() 0 20 2
A getAttributes() 0 13 3
A __construct() 0 6 1
A getServices() 0 15 2
1
<?php
2
3
namespace App\Saml;
4
5
use App\Entity\ServiceAttribute;
6
use App\Entity\ServiceAttributeValueInterface;
7
use App\Entity\ServiceProvider;
8
use App\Entity\User;
9
use App\Repository\ServiceAttributeRepository;
10
use App\Service\AttributeResolver;
11
use App\Service\UserServiceProviderResolver;
12
use App\Traits\ArrayTrait;
13
use LightSaml\ClaimTypes;
14
use LightSaml\Model\Assertion\Attribute;
15
use SchulIT\CommonBundle\Saml\ClaimTypes as ExtendedClaimTypes;
16
use SchulIT\LightSamlIdpBundle\Provider\Attribute\AbstractAttributeProvider;
17
use Symfony\Component\Security\Core\Authentication\Token\Storage\TokenStorageInterface;
18
use Symfony\Component\Security\Core\User\UserInterface;
19
20
/**
21
 * Helper class which is used in LightSAML to determine attributes for a user.
22
 */
23
class AttributeValueProvider extends AbstractAttributeProvider {
24
25
    use ArrayTrait;
26
27
    private $attributeResolver;
28
    private $attributeRepository;
29
    private $userServiceProviderResolver;
30
31 1
    public function __construct(TokenStorageInterface $tokenStorage, AttributeResolver $attributeResolver, ServiceAttributeRepository $attributeRepository, UserServiceProviderResolver $userServiceProviderResolver) {
32 1
        parent::__construct($tokenStorage);
33
34 1
        $this->attributeResolver = $attributeResolver;
35 1
        $this->attributeRepository = $attributeRepository;
36 1
        $this->userServiceProviderResolver = $userServiceProviderResolver;
37 1
    }
38
39
    /**
40
     * Returns a list of common attributes which should always be included in a SAMLResponse
41
     *
42
     * @param User|null $user
43
     * @return array
44
     */
45
    public function getCommonAttributesForUser(User $user = null) {
46
        if($user === null) {
47
            return [ ];
48
        }
49
50
        $attributes = [ ];
51
52
        $attributes[ExtendedClaimTypes::ID] = $user->getUuid();
53
        $attributes[ClaimTypes::SURNAME] = $user->getLastname();
54
        $attributes[ClaimTypes::GIVEN_NAME] = $user->getFirstname();
55
        $attributes[ClaimTypes::EMAIL_ADDRESS] = $user->getEmail();
56
        $attributes[ExtendedClaimTypes::EXTERNAL_ID] =  $user->getExternalId();
57
        $attributes[ExtendedClaimTypes::SERVICES] = $this->getServices($user);
58
        $attributes[ExtendedClaimTypes::GRADE] = $user->getGrade();
59
        $attributes[ExtendedClaimTypes::TYPE] = $user->getType()->getAlias();
60
61
        // eduPersonAffiliation
62
        $attributes[ExtendedClaimTypes::EDU_PERSON_AFFILIATION] = $user->getType()->getEduPerson();
63
64
        return $attributes;
65
    }
66
67
    /**
68
     * @param string $entityId
69
     * @return ServiceAttribute[]
70
     */
71
    private function getRequestedAttributes($entityId) {
72
        $attributes = $this->attributeRepository->getAttributesForServiceProvider($entityId);
73
74
        return $this->makeArrayWithKeys($attributes, function(ServiceAttribute $attribute) {
75
            return $attribute->getId();
76
        });
77
    }
78
79
    /**
80
     * @param User $user
81
     * @return ServiceAttributeValueInterface[]
82
     */
83
    private function getUserAttributeValues(User $user) {
84
        $attributeValues = $this->attributeResolver
85
            ->getDetailedResultingAttributeValuesForUser($user);
86
87
        return $this->makeArrayWithKeys($attributeValues, function(ServiceAttributeValueInterface $attributeValue) {
88
            return $attributeValue->getAttribute()->getId();
89
        });
90
    }
91
92
    /**
93
     * Returns a list of attributes for the given user and the given entityId (of the requested service provider).
94
     *
95
     * @param string $entityId
96
     * @param User $user
97
     * @return string[]
98
     */
99
    private function getAttributes($entityId, User $user) {
100
        $attributes = [ ];
101
102
        $requestedAttributes = $this->getRequestedAttributes($entityId);
103
        $userAttributes = $this->getUserAttributeValues($user);
104
105
        foreach($requestedAttributes as $attributeId => $requestedAttribute) {
106
            if(array_key_exists($attributeId, $userAttributes)) {
107
                $attributes[$requestedAttribute->getSamlAttributeName()] = $userAttributes[$attributeId]->getValue();
108
            }
109
        }
110
111
        return $attributes;
112
    }
113
114
    /**
115
     * @param UserInterface $user
116
     * @param string $entityId
117
     * @return Attribute[]
118
     */
119
    public function getValuesForUser(UserInterface $user, $entityId) {
120
        $attributes = [ ];
121
122
        $attributes[] = new Attribute(ClaimTypes::COMMON_NAME, $user->getUsername());
123
124
        if(!$user instanceof User) {
125
            return $attributes;
126
        }
127
128
        foreach($this->getCommonAttributesForUser($user) as $name => $value) {
129
            $attributes[] = new Attribute($name, $value);
130
        }
131
132
        $userAttributes = $this->getAttributes($entityId, $user);
133
134
        foreach($userAttributes as $samlAttributeName => $value) {
135
            $attributes[] = new Attribute($samlAttributeName, $value);
136
        }
137
138
        return $attributes;
139
    }
140
141
142
    protected function getServices(User $user) {
143
        /** @var ServiceProvider[] $services */
144
        $services = $this->userServiceProviderResolver->getServices($user);
145
146
        $attributeValue = [ ];
147
148
        foreach($services as $service) {
149
            $attributeValue[] = json_encode([
150
                'url' => $service->getUrl(),
151
                'name' => $service->getName(),
152
                'description' => $service->getDescription()
153
            ], JSON_HEX_AMP | JSON_HEX_TAG);
154
        }
155
156
        return $attributeValue;
157
    }
158
}