Passed
Push — master ( 4c08a2...19d2d9 )
by Damien
03:42
created

TokenStorageUserProvider::getImpersonatorUser()   B

Complexity

Conditions 7
Paths 19

Size

Total Lines 24
Code Lines 11

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 7
eloc 11
nc 19
nop 0
dl 0
loc 24
rs 8.8333
c 1
b 0
f 0
1
<?php
2
3
namespace DH\DoctrineAuditBundle\User;
4
5
use Exception;
6
use Symfony\Component\Security\Core\Authentication\Token\SwitchUserToken;
7
use Symfony\Component\Security\Core\Role\SwitchUserRole;
8
use Symfony\Component\Security\Core\Security;
9
use Symfony\Component\Security\Core\User\UserInterface as BaseUserInterface;
10
11
class TokenStorageUserProvider implements UserProviderInterface
12
{
13
    private $security;
14
15
    public function __construct(Security $security)
16
    {
17
        $this->security = $security;
18
    }
19
20
    /**
21
     * @return null|UserInterface
22
     */
23
    public function getUser(): ?UserInterface
24
    {
25
        try {
26
            $token = $this->security->getToken();
27
        } catch (Exception $e) {
28
            $token = null;
29
        }
30
31
        if (null === $token) {
32
            return null;
33
        }
34
35
        $tokenUser = $token->getUser();
36
        if (!($tokenUser instanceof BaseUserInterface)) {
37
            return null;
38
        }
39
40
        $impersonation = '';
41
        if ($this->security->isGranted('ROLE_PREVIOUS_ADMIN')) {
42
            // Symfony > 4.3
43
            if ($token instanceof SwitchUserToken) {
44
                $impersonatorUser = $token->getOriginalToken()->getUser();
45
            } else {
46
                $impersonatorUser = $this->getImpersonatorUser();
47
            }
48
49
            if (\is_object($impersonatorUser)) {
50
                $id = method_exists($impersonatorUser, 'getId') ? $impersonatorUser->getId() : null;
51
                $username = method_exists($impersonatorUser, 'getUsername') ? $impersonatorUser->getUsername() : (string) $impersonatorUser;
52
                $impersonation = ' [impersonator '.$username.':'.$id.']';
53
            }
54
        }
55
        $id = method_exists($tokenUser, 'getId') ? $tokenUser->getId() : null;
56
57
        return new User($id, $tokenUser->getUsername().$impersonation);
58
    }
59
60
    /**
61
     * @return null|Security
62
     */
63
    public function getSecurity(): ?Security
64
    {
65
        return $this->security;
66
    }
67
68
    private function getImpersonatorUser()
69
    {
70
        $token = $this->security->getToken();
71
72
        // Symfony 5
73
        if (class_exists('\Symfony\Component\Security\Core\Authentication\Token\SwitchUserToken')) {
74
            if ($token instanceof SwitchUserToken) {
75
                return $token->getOriginalToken()->getUser();
76
            }
77
        }
78
79
        // Pre Symfony 5
80
        $roles = [];
81
        if (null !== $token) {
82
            $roles = method_exists($token, 'getRoleNames') ? $token->getRoleNames() : $token->getRoles();
83
        }
84
85
        foreach ($roles as $role) {
86
            if ($role instanceof SwitchUserRole) {
87
                return $role->getSource()->getUser();
88
            }
89
        }
90
91
        return null;
92
    }
93
}
94