Completed
Push — V6 ( 927ad1...3487d5 )
by Georges
03:17
created

CacheItemPoolTrait::getItem()   C

Complexity

Conditions 9
Paths 8

Size

Total Lines 63
Code Lines 27

Duplication

Lines 0
Ratio 0 %

Importance

Changes 5
Bugs 3 Features 1
Metric Value
cc 9
eloc 27
c 5
b 3
f 1
nc 8
nop 1
dl 0
loc 63
rs 6.6149

How to fix   Long Method   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
2
/**
3
 *
4
 * This file is part of phpFastCache.
5
 *
6
 * @license MIT License (MIT)
7
 *
8
 * For full copyright and license information, please see the docs/CREDITS.txt file.
9
 *
10
 * @author Khoa Bui (khoaofgod)  <[email protected]> http://www.phpfastcache.com
11
 * @author Georges.L (Geolim4)  <[email protected]>
12
 *
13
 */
14
15
namespace phpFastCache\Core\Pool;
16
17
use phpFastCache\Core\Item\ExtendedCacheItemInterface;
18
use phpFastCache\CacheManager;
19
use phpFastCache\EventManager;
20
use phpFastCache\Exceptions\phpFastCacheCoreException;
21
use Psr\Cache\CacheItemInterface;
22
use phpFastCache\Util\ClassNamespaceResolverTrait;
23
24
/**
25
 * Trait StandardPsr6StructureTrait
26
 * @package phpFastCache\Core
27
 *
28
 */
29
trait CacheItemPoolTrait
30
{
31
    use ClassNamespaceResolverTrait;
32
33
    /**
34
     * @var array
35
     */
36
    protected $deferredList = [];
37
38
    /**
39
     * @var ExtendedCacheItemInterface[]
40
     */
41
    protected $itemInstances = [];
42
43
    /**
44
     * @var EventManager
45
     */
46
    protected $eventManager;
47
48
    /**
49
     * @param string $key
50
     * @return \phpFastCache\Core\Item\ExtendedCacheItemInterface
51
     * @throws \InvalidArgumentException
52
     * @throws \LogicException
53
     * @throws phpFastCacheCoreException
54
     */
55
    public function getItem($key)
56
    {
57
        if (is_string($key)) {
58
            if (!array_key_exists($key, $this->itemInstances)) {
59
60
                /**
61
                 * @var $item ExtendedCacheItemInterface
62
                 */
63
                CacheManager::$ReadHits++;
64
                $class = new \ReflectionClass((new \ReflectionObject($this))->getNamespaceName() . '\Item');
65
                $item = $class->newInstanceArgs([$this, $key]);
66
                $item->setEventManager($this->eventManager);
67
                $driverArray = $this->driverRead($item);
68
69
                if ($driverArray) {
70
                    if(!is_array($driverArray)){
71
                        throw new phpFastCacheCoreException(sprintf('The driverRead method returned an unexpected variable type: %s', gettype($driverArray)));
72
                    }
73
                    $item->set($this->driverUnwrapData($driverArray));
74
                    $item->expiresAt($this->driverUnwrapEdate($driverArray));
75
76
                    if($this->config['itemDetailedDate']){
0 ignored issues
show
Bug introduced by
The property config does not exist. Did you maybe forget to declare it?

In PHP it is possible to write to properties without declaring them. For example, the following is perfectly valid PHP code:

class MyClass { }

$x = new MyClass();
$x->foo = true;

Generally, it is a good practice to explictly declare properties to avoid accidental typos and provide IDE auto-completion:

class MyClass {
    public $foo;
}

$x = new MyClass();
$x->foo = true;
Loading history...
77
78
                        /**
79
                         * If the itemDetailedDate has been
80
                         * set after caching, we MUST inject
81
                         * a new DateTime object on the fly
82
                         */
83
                        $item->setCreationDate($this->driverUnwrapCdate($driverArray) ?: new \DateTime());
84
                        $item->setModificationDate($this->driverUnwrapMdate($driverArray) ?: new \DateTime());
85
                    }
86
87
                    $item->setTags($this->driverUnwrapTags($driverArray));
88
                    if ($item->isExpired()) {
89
                        /**
90
                         * Using driverDelete() instead of delete()
91
                         * to avoid infinite loop caused by
92
                         * getItem() call in delete() method
93
                         * As we MUST return an item in any
94
                         * way, we do not de-register here
95
                         */
96
                        $this->driverDelete($item);
97
                    } else {
98
                        $item->setHit(true);
99
                    }
100
                }else{
101
                    $item->expiresAfter(abs((int) $this->getConfig()[ 'defaultTtl' ]));
102
                }
103
104
            }
105
        } else {
106
            throw new \InvalidArgumentException(sprintf('$key must be a string, got type "%s" instead.', gettype($key)));
107
        }
108
109
        /**
110
         * @eventName CacheGetItem
111
         * @param $this ExtendedCacheItemPoolInterface
112
         * @param $this ExtendedCacheItemInterface
113
         */
114
        $this->eventManager->dispatch('CacheGetItem', $this, $this->itemInstances[ $key ]);
115
116
        return $this->itemInstances[ $key ];
117
    }
118
119
    /**
120
     * @param \Psr\Cache\CacheItemInterface $item
121
     * @return $this
122
     * @throws \InvalidArgumentException
123
     */
124
    public function setItem(CacheItemInterface $item)
125
    {
126
        if ($this->getClassNamespace() . '\\Item' === get_class($item)) {
127
            $this->itemInstances[ $item->getKey() ] = $item;
128
129
            return $this;
130
        } else {
131
            throw new \InvalidArgumentException(sprintf('Invalid Item Class "%s" for this driver.', get_class($item)));
132
        }
133
    }
134
135
    /**
136
     * @param array $keys
137
     * @return CacheItemInterface[]
138
     * @throws \InvalidArgumentException
139
     */
140
    public function getItems(array $keys = [])
141
    {
142
        $collection = [];
143
        foreach ($keys as $key) {
144
            $collection[ $key ] = $this->getItem($key);
145
        }
146
147
        return $collection;
148
    }
149
150
    /**
151
     * @param string $key
152
     * @return bool
153
     * @throws \InvalidArgumentException
154
     */
155
    public function hasItem($key)
156
    {
157
        CacheManager::$ReadHits++;
158
159
        return $this->getItem($key)->isHit();
160
    }
161
162
    /**
163
     * @return bool
164
     */
165
    public function clear()
166
    {
167
        /**
168
         * @eventName CacheClearItem
169
         * @param $this ExtendedCacheItemPoolInterface
170
         * @param $deferredList ExtendedCacheItemInterface[]
171
         */
172
        $this->eventManager->dispatch('CacheClearItem', $this, $this->itemInstances);
173
174
        CacheManager::$WriteHits++;
175
        $this->itemInstances = [];
176
177
        return $this->driverClear();
178
    }
179
180
    /**
181
     * @param string $key
182
     * @return bool
183
     * @throws \InvalidArgumentException
184
     */
185
    public function deleteItem($key)
186
    {
187
        $item = $this->getItem($key);
188
        if ($this->hasItem($key) && $this->driverDelete($item)) {
189
            $item->setHit(false);
190
            CacheManager::$WriteHits++;
191
            /**
192
             * De-register the item instance
193
             * then collect gc cycles
194
             */
195
            $this->deregisterItem($key);
196
197
            return true;
198
        }
199
200
        return false;
201
    }
202
203
    /**
204
     * @param array $keys
205
     * @return bool
206
     * @throws \InvalidArgumentException
207
     */
208
    public function deleteItems(array $keys)
209
    {
210
        $return = null;
211
        foreach ($keys as $key) {
212
            $result = $this->deleteItem($key);
213
            if ($result !== false) {
214
                $return = $result;
215
            }
216
        }
217
218
        return (bool) $return;
219
    }
220
221
    /**
222
     * @param \Psr\Cache\CacheItemInterface $item
223
     * @return mixed
224
     * @throws \InvalidArgumentException
225
     * @throws \RuntimeException
226
     */
227
    public function save(CacheItemInterface $item)
228
    {
229
        /**
230
         * @var ExtendedCacheItemInterface $item
231
         */
232 View Code Duplication
        if (!array_key_exists($item->getKey(), $this->itemInstances)) {
1 ignored issue
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
233
            $this->itemInstances[ $item->getKey() ] = $item;
234
        } else if(spl_object_hash($item) !== spl_object_hash($this->itemInstances[ $item->getKey() ])){
235
            throw new \RuntimeException('Spl object hash mismatches ! You probably tried to save a detached item which has been already retrieved from cache.');
236
        }
237
238
        /**
239
         * @eventName CacheSaveItem
240
         * @param $this ExtendedCacheItemPoolInterface
241
         * @param $this ExtendedCacheItemInterface
242
         */
243
        $this->eventManager->dispatch('CacheSaveItem', $this, $item);
244
245
        if ($this->driverWrite($item) && $this->driverWriteTags($item)) {
246
            $item->setHit(true);
247
            CacheManager::$WriteHits++;
248
249
            return true;
250
        }
251
252
        return false;
253
    }
254
255
256
    /**
257
     * @param \Psr\Cache\CacheItemInterface $item
258
     * @return \Psr\Cache\CacheItemInterface
259
     * @throws \RuntimeException
260
     */
261
    public function saveDeferred(CacheItemInterface $item)
262
    {
263 View Code Duplication
        if (!array_key_exists($item->getKey(), $this->itemInstances)) {
1 ignored issue
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
264
            $this->itemInstances[ $item->getKey() ] = $item;
265
        }else if(spl_object_hash($item) !== spl_object_hash($this->itemInstances[ $item->getKey() ])){
266
            throw new \RuntimeException('Spl object hash mismatches ! You probably tried to save a detached item which has been already retrieved from cache.');
267
        }
268
269
        /**
270
         * @eventName CacheSaveDeferredItem
271
         * @param $this ExtendedCacheItemPoolInterface
272
         * @param $this ExtendedCacheItemInterface
273
         */
274
        $this->eventManager->dispatch('CacheSaveDeferredItem', $this, $item);
275
276
        return $this->deferredList[ $item->getKey() ] = $item;
277
    }
278
279
    /**
280
     * @return mixed|null
281
     * @throws \InvalidArgumentException
282
     */
283
    public function commit()
284
    {
285
        /**
286
         * @eventName CacheCommitItem
287
         * @param $this ExtendedCacheItemPoolInterface
288
         * @param $deferredList ExtendedCacheItemInterface[]
289
         */
290
        $this->eventManager->dispatch('CacheCommitItem', $this, $this->deferredList);
291
292
        $return = null;
293
        foreach ($this->deferredList as $key => $item) {
294
            $result = $this->save($item);
295
            if ($return !== false) {
296
                unset($this->deferredList[ $key ]);
297
                $return = $result;
298
            }
299
        }
300
301
        return (bool) $return;
302
    }
303
}