Passed
Push — master ( 53eeea...c4621c )
by Mārtiņš
02:52
created

StandardIdentity   A

Complexity

Total Complexity 15

Size/Duplication

Total Lines 192
Duplicated Lines 0 %

Test Coverage

Coverage 48.15%

Importance

Changes 0
Metric Value
wmc 15
dl 0
loc 192
c 0
b 0
f 0
ccs 39
cts 81
cp 0.4815
rs 10

8 Methods

Rating   Name   Duplication   Size   Complexity  
B fetchByIdentifier() 0 31 3
A exists() 0 20 1
A bindToken() 0 12 2
A fetch() 0 8 2
A store() 0 8 2
B fetchById() 0 30 3
B updateIdentity() 0 28 1
A createIdentity() 0 20 1
1
<?php
2
3
namespace Palladium\Mapper;
4
5
/**
6
 * SQL logic for authentication attempts using username/password
7
 */
8
9
use Palladium\Component\DataMapper;
10
use Palladium\Entity as Entity;
11
use PDOStatement;
12
use PDO;
13
14
class StandardIdentity extends DataMapper
15
{
16
17
    /**
18
     * @param Entity\StandardIdentity $entity
19
     */
20
    public function exists(Entity\StandardIdentity $entity)
21
    {
22
        $sql = "SELECT 1
23
                  FROM {$this->table}
24
                 WHERE type = :type
25
                   AND fingerprint = :fingerprint
26
                   AND identifier = :identifier
27
                   AND (expires_on IS NULL OR expires_on > :now)";
28
29
        $statement = $this->connection->prepare($sql);
30
31
        $statement->bindValue(':type', Entity\StandardIdentity::TYPE_EMAIL);
32
        $statement->bindValue(':fingerprint', $entity->getFingerprint());
33
        $statement->bindValue(':identifier', $entity->getIdentifier());
34
        $statement->bindValue(':now', time());
35
36
        $statement->execute();
37
        $data = $statement->fetch(PDO::FETCH_ASSOC);
38
39
        return empty($data) === false;
40
    }
41
42
43
    /**
44
     * @param Entity\StandardIdentity $entity
45
     */
46
    public function fetch(Entity\StandardIdentity $entity)
47
    {
48
        if ($entity->getId()) {
49
            $this->fetchById($entity);
50
            return;
51
        }
52
53
        $this->fetchByIdentifier($entity);
54
    }
55
56
57
    private function fetchByIdentifier(Entity\StandardIdentity $entity)
58
    {
59
        $sql = "SELECT identity_id      AS id,
60
                       account_id       AS accountId,
61
                       hash             AS hash,
62
                       status           AS status,
63
                       used_on          AS lastUsed,
64
                       token            AS token,
65
                       token_action     AS tokenAction,
66
                       token_expires_on AS tokenEndOfLife,
67
                       token_payload    AS tokenPayload
68
                  FROM {$this->table}
69
                 WHERE type = :type
70
                   AND fingerprint = :fingerprint
71
                   AND identifier = :identifier";
72
73
        $statement = $this->connection->prepare($sql);
74
75
        $statement->bindValue(':type', $entity->getType());
76
        $statement->bindValue(':identifier', $entity->getIdentifier());
77
        $statement->bindValue(':fingerprint', $entity->getFingerprint());
78
79
        $statement->execute();
80
81
        $data = $statement->fetch(PDO::FETCH_ASSOC);
82
83
        if ($data) {
84
            if ($data['tokenPayload'] !== null) {
85
                $data['tokenPayload'] = json_decode($data['tokenPayload'], true);
86
            }
87
            $this->applyValues($entity, $data);
88
        }
89
    }
90
91
92
    private function fetchById(Entity\StandardIdentity $entity)
93
    {
94
        $sql = "SELECT identity_id      AS id,
95
                       identifier       AS identifier,
96
                       account_id       AS accountId,
97
                       hash             AS hash,
98
                       status           AS status,
99
                       used_on          AS lastUsed,
100
                       token            AS token,
101
                       token_action     AS tokenAction,
102
                       token_expires_on AS tokenEndOfLife,
103
                       token_payload    AS tokenPayload
104
                  FROM {$this->table}
105
                 WHERE type = :type
106
                   AND identity_id = :id";
107
108
        $statement = $this->connection->prepare($sql);
109
110
        $statement->bindValue(':type', $entity->getType());
111
        $statement->bindValue(':id', $entity->getId());
112
113
        $statement->execute();
114
115
        $data = $statement->fetch(PDO::FETCH_ASSOC);
116
117
        if ($data) {
118
            if ($data['tokenPayload'] !== null) {
119
                $data['tokenPayload'] = json_decode($data['tokenPayload'], true);
120
            }
121
            $this->applyValues($entity, $data);
122
        }
123
    }
124
125
126
    /**
127
     * @param Entity\StandardIdentity $entity
128
     */
129 2
    public function store(Entity\StandardIdentity $entity)
130
    {
131 2
        if ($entity->getId() === null) {
132 1
            $this->createIdentity($entity);
133 1
            return;
134
        }
135
136 1
        $this->updateIdentity($entity);
137 1
    }
138
139
140 1
    private function createIdentity(Entity\StandardIdentity $entity)
141
    {
142 1
        $sql = "INSERT INTO {$this->table}
143
                       (type, status, identifier, fingerprint, hash, created_on, token, token_action, token_expires_on, token_payload)
144
                VALUES (:type, :status, :identifier, :fingerprint, :hash, :created, :token, :action, :token_eol, :payload)";
145
146 1
        $statement = $this->connection->prepare($sql);
147
148 1
        $statement->bindValue(':type', Entity\StandardIdentity::TYPE_EMAIL);
149 1
        $statement->bindValue(':status', Entity\StandardIdentity::STATUS_NEW);
150 1
        $statement->bindValue(':identifier', $entity->getIdentifier());
151 1
        $statement->bindValue(':fingerprint', $entity->getFingerprint());
152 1
        $statement->bindValue(':hash', $entity->getHash());
153 1
        $statement->bindValue(':created', time());
154
155 1
        $this->bindToken($statement, $entity);
156
157 1
        $statement->execute();
158
159 1
        $entity->setId($this->connection->lastInsertId());
160 1
    }
161
162
163 1
    private function updateIdentity(Entity\StandardIdentity $entity)
164
    {
165 1
        $sql = "UPDATE {$this->table}
166
                   SET hash = :hash,
167
                       identifier = :identifier,
168
                       fingerprint = :fingerprint,
169
                       status = :status,
170
                       used_on = :used,
171
                       expires_on = :expires,
172
                       token = :token,
173
                       token_action = :action,
174
                       token_expires_on = :token_eol,
175
                       token_payload = :payload
176
                 WHERE identity_id = :id";
177
178 1
        $statement = $this->connection->prepare($sql);
179
180 1
        $statement->bindValue(':id', $entity->getId());
181 1
        $statement->bindValue(':hash', $entity->getHash());
182 1
        $statement->bindValue(':identifier', $entity->getIdentifier());
183 1
        $statement->bindValue(':fingerprint', $entity->getFingerprint());
184 1
        $statement->bindValue(':status', $entity->getStatus());
185 1
        $statement->bindValue(':used', $entity->getLastUsed());
186 1
        $statement->bindValue(':expires', $entity->getExpiresOn());
187
188 1
        $this->bindToken($statement, $entity);
189
190 1
        $statement->execute();
191 1
    }
192
193
194 2
    private function bindToken(PDOStatement $statement, Entity\StandardIdentity $entity)
195
    {
196 2
        $statement->bindValue(':token', $entity->getToken());
197 2
        $statement->bindValue(':action', $entity->getTokenAction());
198 2
        $statement->bindValue(':token_eol', $entity->getTokenEndOfLife());
199
200 2
        $payload = $entity->getTokenPayload();
201 2
        if ($payload !== null) {
202
            $payload = json_encode($payload);
203
        }
204
205 2
        $statement->bindValue(':payload', $payload);
206 2
    }
207
}
208