Completed
Pull Request — master (#64)
by Emanuele
03:40 queued 12s
created

FeatureSecurity   A

Complexity

Total Complexity 10

Size/Duplication

Total Lines 92
Duplicated Lines 0 %

Test Coverage

Coverage 97.37%

Importance

Changes 2
Bugs 1 Features 0
Metric Value
eloc 41
c 2
b 1
f 0
dl 0
loc 92
ccs 37
cts 38
cp 0.9737
rs 10
wmc 10

3 Methods

Rating   Name   Duplication   Size   Complexity  
A isGrantedForUser() 0 16 1
B isGranted() 0 41 8
A __construct() 0 9 1
1
<?php
2
3
namespace Ae\FeatureBundle\Security;
4
5
use Ae\FeatureBundle\Entity\Feature;
6
use Psr\Log\LoggerAwareInterface;
7
use Psr\Log\LoggerAwareTrait;
8
use Psr\Log\NullLogger;
9
use Symfony\Component\Security\Core\Authentication\Token\Storage\TokenStorageInterface;
10
use Symfony\Component\Security\Core\Authentication\Token\UsernamePasswordToken;
11
use Symfony\Component\Security\Core\Authorization\AuthorizationCheckerInterface;
12
use Symfony\Component\Security\Core\User\UserInterface;
13
14
/**
15
 * Controls access to a Feature.
16
 *
17
 * @author Carlo Forghieri <[email protected]>
18
 */
19
class FeatureSecurity implements LoggerAwareInterface
20
{
21
    use LoggerAwareTrait;
22
23
    /**
24
     * @param AuthorizationCheckerInterface
25
     */
26
    protected $context;
27
28
    /**
29
     * @param TokenStorageInterface
30
     */
31
    private $storage;
32
33
    /**
34
     * @param string
35
     */
36
    private $providerKey;
37
38 9
    public function __construct(
39
        AuthorizationCheckerInterface $context,
40
        TokenStorageInterface $storage,
41
        string $providerKey
42
    ) {
43 9
        $this->context = $context;
44 9
        $this->storage = $storage;
45 9
        $this->providerKey = $providerKey;
46 9
        $this->logger = new NullLogger();
47 9
    }
48
49
    /**
50
     * @return bool
51
     */
52 7
    public function isGranted(Feature $feature)
53
    {
54 7
        if ($feature->isExpired()) {
55 1
            $message = sprintf(
56 1
                'The feature "%s.%s" class is deprecated since %s and should be removed.',
57
                $feature
58 1
                    ->getParent()
59 1
                    ->getName(),
60 1
                $feature->getName(),
61
                $feature
62 1
                    ->getExpiration()
63 1
                    ->format('Y-m-d')
64
            );
65
66 1
            @trigger_error($message, E_USER_DEPRECATED);
67 1
            $this->logger->warning($message);
68
        }
69
70
        // feature is enabled without required roles
71
        // there's no need to check on user roles
72 7
        if (!$feature->requiresRoleCheck()) {
73 3
            return $feature->isEnabled();
74
        }
75
76 4
        if (!$feature->isEnabled()) {
77 1
            return false;
78
        }
79
80 3
        if ($feature->getRole()) {
81 2
            if (!$this->context->isGranted($feature->getRole())) {
82
                return false;
83
            }
84
        }
85
86 3
        if ('' !== trim($feature->getParentRole())) {
87 1
            if (!$this->context->isGranted($feature->getParentRole())) {
88 1
                return false;
89
            }
90
        }
91
92 2
        return true;
93
    }
94
95 2
    public function isGrantedForUser(Feature $feature, UserInterface $user): bool
96
    {
97 2
        $oldToken = $this->storage->getToken();
98
99 2
        $this->storage->setToken(new UsernamePasswordToken(
100 2
            $user,
101 2
            null,
102 2
            $this->providerKey,
103 2
            $user->getRoles()
104
        ));
105
106 2
        $granted = $this->isGranted($feature);
107
108 2
        $this->storage->setToken($oldToken);
109
110 2
        return $granted;
111
    }
112
}
113