LdapManager::findUserBy()   B
last analyzed

Complexity

Conditions 7
Paths 6

Size

Total Lines 26
Code Lines 17

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 12
CRAP Score 8.2464

Importance

Changes 2
Bugs 0 Features 0
Metric Value
cc 7
eloc 17
c 2
b 0
f 0
nc 6
nop 1
dl 0
loc 26
ccs 12
cts 17
cp 0.7059
crap 8.2464
rs 8.8333
1
<?php
2
3
namespace DoL\LdapBundle\Ldap;
4
5
use DoL\LdapBundle\Driver\LdapDriverInterface;
6
use DoL\LdapBundle\Event\SwitchParameterSetEvent;
7
use Symfony\Component\EventDispatcher\EventDispatcherInterface;
8
use Symfony\Component\Security\Core\User\UserInterface;
9
use DoL\LdapBundle\Hydrator\HydratorInterface;
10
11
/**
12
 * Ldap manager for multi-domains.
13
 *
14
 * @author DarwinOnLine
15
 * @author Maks3w
16
 *
17
 * @see https://github.com/DarwinOnLine/DoLLdapBundle
18
 */
19
class LdapManager implements LdapManagerInterface
20
{
21
    protected $driver;
22
    protected $paramSets = [];
23
24
    protected $params = [];
25
    protected $ldapAttributes = [];
26
    protected $ldapUsernameAttr;
27
    /**
28
     * @var EventDispatcherInterface
29
     */
30
    protected $eventDispatcher;
31 4
32
    /**
33 4
     * @var HydratorInterface
34 4
     */
35 4
    protected $hydrator;
36 4
37
    public function __construct(LdapDriverInterface $driver, HydratorInterface $hydrator, EventDispatcherInterface $eventDispatcher, array $paramSets)
38
    {
39
        $this->driver = $driver;
40
        $this->hydrator = $hydrator;
41 1
        $this->eventDispatcher = $eventDispatcher;
42
        $this->paramSets = $paramSets;
43 1
    }
44
45
    /**
46 1
     * {@inheritdoc}
47 1
     */
48
    public function bind(UserInterface $user, $password)
49 1
    {
50 1
        if (!empty($this->params)) {
51 1
            return $this->driver->bind($user, $password);
52
        } else {
53 1
            foreach ($this->paramSets as $paramSet) {
54
                $this->driver->init($paramSet['driver']);
55
56
                if (false !== $this->driver->bind($user, $password)) {
57
                    $this->switchParameterSet($paramSet);
58
59
                    return true;
60
                }
61
            }
62
        }
63
64 1
        return false;
65
    }
66 1
67
    /**
68
     * {@inheritdoc}
69 1
     */
70 1
    public function findUserByUsername($username)
71 1
    {
72 1
        if (!empty($this->params)) {
73
            return $this->findUserBy([$this->ldapUsernameAttr => $username]);
74 1
        } else {
75 1
            foreach ($this->paramSets as $paramSet) {
76 1
                $this->driver->init($paramSet['driver']);
77
                $this->switchParameterSet($paramSet);
78
79
                $user = $this->findUserBy([$this->ldapUsernameAttr => $username]);
80
                if (false !== $user && $user instanceof UserInterface) {
81
                    return $user;
82
                }
83
84
                $this->switchParameterSet([]);
85
            }
86
        }
87
    }
88 2
89
    /**
90 2
     * {@inheritdoc}
91 2
     */
92 2
    public function findUserBy(array $criteria)
93 2
    {
94
        if (!empty($this->params)) {
95
            $filter = $this->buildFilter($criteria);
96
            $entries = $this->driver->search($this->params['baseDn'], $filter);
97 2
            if ($entries['count'] > 1) {
98
                throw new \Exception('This search can only return a single user');
99
            }
100 2
101
            if (0 == $entries['count']) {
102 2
                return null;
103
            }
104 1
            $user = $this->hydrator->hydrate($entries[0]);
105 1
106 1
            return $user;
107 1
        } else {
108
            foreach ($this->paramSets as $paramSet) {
109 1
                $this->driver->init($paramSet['driver']);
110 1
                $this->switchParameterSet($paramSet);
111 1
112
                $user = $this->findUserBy($criteria);
113
                if (false !== $user && $user instanceof UserInterface) {
114
                    return $user;
115
                }
116
117
                $this->switchParameterSet([]);
118
            }
119
        }
120
    }
121
122
    /**
123 3
     * Sets temp Ldap attributes.
124
     */
125 3
    private function setLdapAttr()
126 3
    {
127
        if (isset($this->params['attributes'])) {
128 3
            $this->hydrator->setAttributeMap($this->params['attributes']);
129 3
130 3
            foreach ($this->params['attributes'] as $attr) {
131
                $this->ldapAttributes[] = $attr['ldap_attr'];
132 3
            }
133 3
134
            $this->ldapUsernameAttr = $this->ldapAttributes[0];
135
        } else {
136
            $this->ldapAttributes = [];
137 3
            $this->ldapUsernameAttr = null;
138
        }
139
    }
140
141
    /**
142
     * Build Ldap filter.
143
     *
144
     * @param array  $criteria
145
     * @param string $condition
146
     *
147 3
     * @return string
148
     */
149 3
    protected function buildFilter(array $criteria, $condition = '&')
150 3
    {
151 3
        $filters = [];
152 3
        if (isset($this->params['filter'])) {
153 3
            $filters[] = $this->params['filter'];
154 3
        }
155 3
        foreach ($criteria as $key => $value) {
156 3
            $value = ldap_escape($value, '', LDAP_ESCAPE_FILTER);
157
            $filters[] = sprintf('(%s=%s)', $key, $value);
158 3
        }
159
160
        return sprintf('(%s%s)', $condition, implode($filters));
161
    }
162
163
    private function switchParameterSet(array $parameter)
164
    {
165
        if (isset($parameter['user'])) {
166
            $this->params = $parameter['user'];
167
        } else {
168
            $this->params = [];
169
        }
170
        $this->setLdapAttr();
171
        $this->eventDispatcher->dispatch(SwitchParameterSetEvent::PARAMETERSET, new SwitchParameterSetEvent($parameter));
172
    }
173
}
174