Completed
Push — master ( a065d6...df6c9b )
by Anton
13s
created

RedisAdapter::getChunkNumsKey()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 4
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 2

Importance

Changes 1
Bugs 0 Features 0
Metric Value
c 1
b 0
f 0
dl 0
loc 4
ccs 0
cts 4
cp 0
rs 10
cc 1
eloc 2
nc 1
nop 1
crap 2
1
<?php
2
/**
3
 * Yandex PHP Library
4
 *
5
 * @copyright NIX Solutions Ltd.
6
 * @link https://github.com/nixsolutions/yandex-php-library
7
 */
8
9
/**
10
 * @namespace
11
 */
12
namespace Yandex\SafeBrowsing\Adapter;
13
14
use Predis\Client;
15
16
/**
17
 * Class RedisAdapter
18
 *
19
 * @category Yandex
20
 * @package SafeBrowsing
21
 */
22
class RedisAdapter
23
{
24
    const KEY_SHA_VARS = 'sha_vars';
25
    const KEY_SHA_VAR = 'sha_var';
26
27
    const KEY_HASH_PREFIXES = 'hash_prefixes';
28
    const KEY_HASH_PREFIX = 'hash_prefix';
29
30
    const KEY_CHUNK_NUMS = 'chunk_nums';
31
    const KEY_CHUNK_NUM = 'chunk_num';
32
33
    /**
34
     * @var Client
35
     */
36
    private $client;
37
38
    public function __construct($dsn = '', $options = [])
39
    {
40
        $this->client = $this->initClient($dsn, $options);
41
    }
42
43
    /**
44
     * @param string $dsn
45
     * @param array $options
46
     * @param bool $reset
47
     * @return Client
48
     */
49
    public function initClient($dsn = '', $options = [], $reset = false)
50
    {
51
        if (!$this->client || $reset) {
52
            $this->client = new Client($dsn, $options);
53
            $this->client->ping();
54
        }
55
56
        return $this->client;
57
    }
58
59
    /**
60
     * @param string $shaVar
61
     */
62
    public function addShaVar($shaVar)
63
    {
64
        $this->client->sadd(self::KEY_SHA_VARS, [$shaVar]);
65
    }
66
67
    /**
68
     * @param string $shaVar
69
     * @param string $chunkNum
70
     */
71
    public function addChunkNum($shaVar, $chunkNum)
72
    {
73
        $key = $this->getChunkNumsKey($shaVar);
74
        $this->client->sadd($key, [$chunkNum]);
75
    }
76
77
    /**
78
     * @param string $shaVar
79
     * @param string $chunkNum
80
     * @param string $hashPrefix
81
     */
82
    public function addHashPrefix($shaVar, $chunkNum, $hashPrefix)
83
    {
84
        $chunkNumKey = $this->getChunkNumKey($shaVar, $chunkNum);
85
        $hashPrefixKey = $this->getHashPrefixKey($hashPrefix);
86
87
        $this->client->sadd($chunkNumKey, [$hashPrefix]);
88
        $this->client->sadd($hashPrefixKey, [$chunkNumKey]);
89
    }
90
91
    /**
92
     * @param string $shaVar
93
     * @param string $chunkNum
94
     * @param string $hashPrefix
95
     */
96
    public function saveHashPrefix($shaVar, $chunkNum, $hashPrefix)
97
    {
98
        $this->addShaVar($shaVar);
99
        $this->addChunkNum($shaVar, $chunkNum);
100
        $this->addHashPrefix($shaVar, $chunkNum, $hashPrefix);
101
    }
102
103
    public function getShaVars()
104
    {
105
        return $this->client->smembers(self::KEY_SHA_VARS);
106
    }
107
108
    /**
109
     * @param string $shaVar
110
     * @return array
111
     */
112
    public function getChunkNums($shaVar)
113
    {
114
        $key = $key = $this->getChunkNumsKey($shaVar);
115
116
        return $this->client->smembers($key);
117
    }
118
119
    /**
120
     * @param string $shaVar
121
     * @param string $chunkNum
122
     * @return array
123
     */
124
    public function getHashPrefixes($shaVar, $chunkNum)
125
    {
126
        $key = $this->getChunkNumKey($shaVar, $chunkNum);
127
128
        return $this->client->smembers($key);
129
    }
130
131
    /**
132
     * @param string $hashPrefix
133
     * @return array
134
     */
135
    public function getHashPrefix($hashPrefix)
136
    {
137
        $key = $this->getHashPrefixKey($hashPrefix);
138
139
        return $this->client->smembers($key);
140
    }
141
142
    /**
143
     * @param string $shaVar
144
     * @param string $chunkNum
145
     */
146
    public function removeChunkNum($shaVar, $chunkNum)
147
    {
148
        $chunkNumsKey = $this->getChunkNumsKey($shaVar);
149
        $chunkNumKey = $this->getChunkNumKey($shaVar, $chunkNum);
150
151
        $hashPrefixes = $this->client->smembers($chunkNumKey);
152
153
        foreach ($hashPrefixes as $hashPrefix) {
154
            $this->removeHashPrefix($shaVar, $chunkNum, $hashPrefix);
155
        }
156
157
        $this->client->srem($chunkNumsKey, $chunkNum);
158
        $this->client->del([$chunkNumKey]);
159
160
        if (0 === $this->client->scard($chunkNumsKey)) {
161
            $this->client->srem(self::KEY_SHA_VARS, $shaVar);
162
        }
163
    }
164
165
    /**
166
     * @param string $shaVar
167
     * @param string $chunkNum
168
     * @param string $hashPrefix
169
     */
170
    public function removeHashPrefix($shaVar, $chunkNum, $hashPrefix)
171
    {
172
        $chunkNumKey = $this->getChunkNumKey($shaVar, $chunkNum);
173
        $hashPrefixKey = $this->getHashPrefixKey($hashPrefix);
174
175
        $this->client->srem($chunkNumKey, $hashPrefix);
176
        $this->client->srem($hashPrefixKey, $chunkNumKey);
177
178
        if (0 === $this->client->scard($chunkNumKey)) {
179
            $this->removeChunkNum($shaVar, $chunkNum);
180
        }
181
    }
182
183
    /**
184
     * @param array $hashes
185
     * @return bool
186
     */
187
    public function hasHashes($hashes)
188
    {
189
        if (!is_array($hashes)) {
190
            return false;
191
        }
192
193
        foreach ($hashes as $hash) {
194
            $key = $this->getHashPrefixKey($hash['prefix']);
195
196
            if (!empty($hash['prefix']) && $this->client->exists($key)) {
197
                return true;
198
            }
199
        }
200
201
        return false;
202
    }
203
204
    /**
205
     * @param array $hashes
206
     * @return array
207
     */
208
    public function getShaVarsByHashes($hashes)
209
    {
210
        if (!is_array($hashes)) {
211
            return [];
212
        }
213
214
        $shaVars = [];
215
216
        foreach ($hashes as $hash) {
217
            if (!empty($hash['prefix']) && $hashPrefixShaVars = $this->getHashPrefix($hash['prefix'])) {
218
                foreach ($hashPrefixShaVars as $hashPrefixShaVar) {
219
                    $shaVars[] = explode(':', $hashPrefixShaVar)[1];
220
                }
221
            }
222
        }
223
224
        return array_unique($shaVars);
225
    }
226
227
    /**
228
     * @param string $shaVar
229
     * @return string
230
     */
231
    private function getChunkNumsKey($shaVar)
232
    {
233
        return sprintf('%s:%s:%s', self::KEY_SHA_VAR, $shaVar, self::KEY_CHUNK_NUMS);
234
    }
235
236
    /**
237
     * @param string $shaVar
238
     * @param string $chunkNum
239
     * @return string
240
     */
241
    private function getChunkNumKey($shaVar, $chunkNum)
242
    {
243
        return sprintf('%s:%s:%s', self::KEY_SHA_VAR, $shaVar, $chunkNum);
244
    }
245
246
    /**
247
     * @param string $hashPrefix
248
     * @return string
249
     */
250
    private function getHashPrefixKey($hashPrefix)
251
    {
252
        return sprintf('%s:%s', self::KEY_HASH_PREFIX, $hashPrefix);
253
    }
254
}
255