Completed
Push — master ( 6a7f55...29301f )
by Lars
02:40
created

Cache   F

Complexity

Total Complexity 91

Size/Duplication

Total Lines 650
Duplicated Lines 3.08 %

Coupling/Cohesion

Components 2
Dependencies 12

Test Coverage

Coverage 44.36%

Importance

Changes 5
Bugs 3 Features 1
Metric Value
wmc 91
lcom 2
cbo 12
dl 20
loc 650
ccs 114
cts 257
cp 0.4436
rs 3.7627
c 5
b 3
f 1

21 Methods

Rating   Name   Duplication   Size   Complexity  
C isCacheActiveForTheCurrentUser() 0 28 7
B getClientIp() 0 18 7
B getTheDefaultPrefix() 0 8 6
F autoConnectToAvailableCacheSystem() 0 148 18
A setCacheIsReady() 0 4 1
A getCacheIsReady() 0 4 1
C __construct() 0 56 13
A setActive() 0 4 1
C checkForDev() 0 29 8
C getItem() 0 49 10
A calculateStoreKey() 0 10 2
B cleanStoreKey() 0 26 1
A getPrefix() 0 4 1
A setPrefix() 0 4 1
A setItemToDate() 0 12 2
A setItem() 0 19 4
A removeItem() 10 10 2
A removeAll() 0 8 2
A existsItem() 10 10 2
A getUsedAdapterClassName() 0 4 1
A getUsedSerializerClassName() 0 4 1

How to fix   Duplicated Code    Complexity   

Duplicated Code

Duplicate code is one of the most pungent code smells. A rule that is often used is to re-structure code once it is duplicated in three or more places.

Common duplication problems, and corresponding solutions are:

Complex Class

 Tip:   Before tackling complexity, make sure that you eliminate any duplication first. This often can reduce the size of classes significantly.

Complex classes like Cache often do a lot of different things. To break such a class down, we need to identify a cohesive component within that class. A common approach to find such a component is to look for fields/methods that share the same prefixes, or suffixes. You can also have a look at the cohesion graph to spot any un-connected, or weakly-connected components.

Once you have determined the fields that belong together, you can apply the Extract Class refactoring. If the component makes sense as a sub-class, Extract Subclass is also a candidate, and is often faster.

While breaking up the class, it is a good idea to analyze how other classes use Cache, and based on these observations, apply Extract Interface, too.

1
<?php
2
3
namespace voku\cache;
4
5
/**
6
 * Cache: global-cache class
7
 *
8
 * can use different cache-adapter:
9
 * - Redis
10
 * - Memcache / Memcached
11
 * - APC / APCu
12
 * - Xcache
13
 * - Array
14
 * - File
15
 *
16
 * @package   voku\cache
17
 */
18
class Cache implements iCache
19
{
20
21
  /**
22
   * @var iAdapter
23
   */
24
  private $adapter;
25
26
  /**
27
   * @var iSerializer
28
   */
29
  private $serializer;
30
31
  /**
32
   * @var string
33
   */
34
  private $prefix = '';
35
36
  /**
37
   * @var bool
38
   */
39
  private $isReady = false;
40
41
  /**
42
   * @var bool
43
   */
44
  private $isActive = true;
45
46
  /**
47
   * @var mixed no cache, if admin-session is set
48
   */
49
  private $isAdminSession = false;
50
51
  /**
52
   * __construct
53
   *
54
   * @param null|iAdapter    $adapter
55
   * @param null|iSerializer $serializer
56
   * @param boolean          $checkForUser   check for dev-ip or if cms-user is logged-in
57
   * @param boolean          $cacheEnabled   false will disable the cache (use it e.g. for global settings)
58
   * @param string|boolean   $isAdminSession set a user-id, if the user is a admin (so we can disable cache for this
59
   *                                         user)
60
   */
61 42
  public function __construct($adapter = null, $serializer = null, $checkForUser = true, $cacheEnabled = true, $isAdminSession = false)
62
  {
63 42
    $this->isAdminSession = $isAdminSession;
64
65
    // First check if the cache is active at all.
66 42
    $this->setActive($cacheEnabled);
67
    if (
68 42
        $this->isActive === true
69 42
        &&
70
        $checkForUser === true
71 42
    ) {
72
      $this->setActive($this->isCacheActiveForTheCurrentUser());
73
    }
74
75
    // If the cache is active, then try to auto-connect to the best possible cache-system.
76 42
    if ($this->isActive === true) {
77
78 42
      $this->setPrefix($this->getTheDefaultPrefix());
79
80
      if (
81
          $adapter === null
82 42
          ||
83 42
          !is_object($adapter)
84 42
          ||
85
          !$adapter instanceof iAdapter
86 42
      ) {
87
        $adapter = $this->autoConnectToAvailableCacheSystem();
88
      }
89
90
      // INFO: Memcache(d) has his own "serializer", so don't use it twice
91 42
      if (!is_object($serializer) && $serializer === null) {
92
        if (
93
            $adapter instanceof AdapterMemcached
94
            ||
95
            $adapter instanceof AdapterMemcache
96
        ) {
97
          $serializer = new SerializerNo();
98
        } else {
99
          // set default serializer
100
          $serializer = new SerializerIgbinary();
101
        }
102
      }
103 42
    }
104
105
    // Final checks ...
106
    if (
107
        $serializer instanceof iSerializer
108 42
        &&
109
        $adapter instanceof iAdapter
110 42
    ) {
111 42
      $this->setCacheIsReady(true);
112
113 42
      $this->adapter = $adapter;
114 42
      $this->serializer = $serializer;
115 42
    }
116 42
  }
117
118
  /**
119
   * enable / disable the cache
120
   *
121
   * @param boolean $isActive
122
   */
123 42
  public function setActive($isActive)
124
  {
125 42
    $this->isActive = (boolean)$isActive;
126 42
  }
127
128
  /**
129
   * check if the current use is a admin || dev || server == client
130
   *
131
   * @return bool
132
   */
133
  public function isCacheActiveForTheCurrentUser()
0 ignored issues
show
Coding Style introduced by
isCacheActiveForTheCurrentUser uses the super-global variable $_GET which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
Coding Style introduced by
isCacheActiveForTheCurrentUser uses the super-global variable $_SERVER which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
134
  {
135
    $active = true;
136
137
    // test the cache, with this GET-parameter
138
    $testCache = isset($_GET['testCache']) ? (int)$_GET['testCache'] : 0;
139
140
    if ($testCache != 1) {
141
      if (
142
        // server == client
143
          (
144
              isset($_SERVER['SERVER_ADDR'])
145
              &&
146
              $_SERVER['SERVER_ADDR'] == $this->getClientIp()
147
          )
148
          ||
149
          // admin is logged-in
150
          $this->isAdminSession
151
          ||
152
          // user is a dev
153
          $this->checkForDev() === true
154
      ) {
155
        $active = false;
156
      }
157
    }
158
159
    return $active;
160
  }
161
162
  /**
163
   * returns the IP address of the client
164
   *
165
   * @param   bool $trust_proxy_headers   Whether or not to trust the
166
   *                                      proxy headers HTTP_CLIENT_IP
167
   *                                      and HTTP_X_FORWARDED_FOR. ONLY
168
   *                                      use if your $_SERVER is behind a
169
   *                                      proxy that sets these values
170
   *
171
   * @return  string
172
   */
173
  private function getClientIp($trust_proxy_headers = false)
0 ignored issues
show
Coding Style introduced by
getClientIp uses the super-global variable $_SERVER which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
174
  {
175
    $remoteAddr = isset($_SERVER['REMOTE_ADDR']) ? $_SERVER['REMOTE_ADDR'] : 'NO_REMOTE_ADDR';
176
177
    if ($trust_proxy_headers) {
178
      return $remoteAddr;
179
    }
180
181
    if (isset($_SERVER['HTTP_CLIENT_IP']) && $_SERVER['HTTP_CLIENT_IP']) {
182
      $ip = $_SERVER['HTTP_CLIENT_IP'];
183
    } elseif (isset($_SERVER['HTTP_X_FORWARDED_FOR']) && $_SERVER['HTTP_X_FORWARDED_FOR']) {
184
      $ip = $_SERVER['HTTP_X_FORWARDED_FOR'];
185
    } else {
186
      $ip = $remoteAddr;
187
    }
188
189
    return $ip;
190
  }
191
192
  /**
193
   * Check for local developer.
194
   *
195
   * @return bool
196
   */
197
  private function checkForDev()
0 ignored issues
show
Coding Style introduced by
checkForDev uses the super-global variable $_GET which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
Coding Style introduced by
checkForDev uses the super-global variable $_SERVER which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
198
  {
199
    $return = false;
200
201
    if (function_exists('checkForDev')) {
202
      $return = checkForDev();
203
    } else {
204
205
      // for testing with dev-address
206
      $noDev = isset($_GET['noDev']) ? (int)$_GET['noDev'] : 0;
207
      $remoteAddr = isset($_SERVER['REMOTE_ADDR']) ? $_SERVER['REMOTE_ADDR'] : 'NO_REMOTE_ADDR';
208
209
      if (
210
          $noDev != 1
211
          &&
212
          (
213
              $remoteAddr === '127.0.0.1'
214
              ||
215
              $remoteAddr === '::1'
216
              ||
217
              PHP_SAPI === 'cli'
218
          )
219
      ) {
220
        $return = true;
221
      }
222
    }
223
224
    return $return;
225
  }
226
227
  /**
228
   * Set the default-prefix via "SERVER"-var + "SESSION"-language.
229
   */
230 42
  protected function getTheDefaultPrefix()
0 ignored issues
show
Coding Style introduced by
getTheDefaultPrefix uses the super-global variable $_SERVER which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
Coding Style introduced by
getTheDefaultPrefix uses the super-global variable $_SESSION which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
231
  {
232 42
    return (isset($_SERVER['SERVER_NAME']) ? $_SERVER['SERVER_NAME'] : '') . '_' .
233 42
           (isset($_SERVER['THEME']) ? $_SERVER['THEME'] : '') . '_' .
234 42
           (isset($_SERVER['STAGE']) ? $_SERVER['STAGE'] : '') . '_' .
235 42
           (isset($_SESSION['language']) ? $_SESSION['language'] : '') . '_' .
236 42
           (isset($_SESSION['language_extra']) ? $_SESSION['language_extra'] : '');
237
  }
238
239
  /**
240
   * Auto-connect to the available cache-system on the server.
241
   *
242
   * @return iAdapter
243
   */
244
  protected function autoConnectToAvailableCacheSystem()
245
  {
246
    static $adapterCache;
247
248
    if (is_object($adapterCache) && $adapterCache instanceof iAdapter) {
249
      return $adapterCache;
250
    } else {
251
252
      $memcached = null;
253
      $isMemcachedAvailable = false;
254
      if (extension_loaded('memcached')) {
255
        $memcached = new \Memcached();
256
        /** @noinspection PhpUsageOfSilenceOperatorInspection */
257
        $isMemcachedAvailable = @$memcached->addServer('127.0.0.1', 11211);
258
      }
259
260
      if ($isMemcachedAvailable === false) {
261
        $memcached = null;
262
      }
263
264
      $adapterMemcached = new AdapterMemcached($memcached);
265
      if ($adapterMemcached->installed() === true) {
266
267
        // -------------------------------------------------------------
268
        // "Memcached"
269
        // -------------------------------------------------------------
270
        $adapter = $adapterMemcached;
271
272
      } else {
273
274
        $memcache = null;
275
        $isMemcacheAvailable = false;
276
        if (class_exists('\Memcache')) {
277
          $memcache = new \Memcache;
278
          /** @noinspection PhpUsageOfSilenceOperatorInspection */
279
          $isMemcacheAvailable = @$memcache->connect('127.0.0.1', 11211);
280
        }
281
282
        if ($isMemcacheAvailable === false) {
283
          $memcache = null;
284
        }
285
286
        $adapterMemcache = new AdapterMemcache($memcache);
287
        if ($adapterMemcache->installed() === true) {
288
289
          // -------------------------------------------------------------
290
          // "Memcache"
291
          // -------------------------------------------------------------
292
          $adapter = $adapterMemcache;
293
294
        } else {
295
296
          $redis = null;
297
          $isRedisAvailable = false;
298
          if (
299
              extension_loaded('redis')
300
              &&
301
              class_exists('\Predis\Client')
302
          ) {
303
            /** @noinspection PhpUndefinedNamespaceInspection */
304
            $redis = new \Predis\Client(
305
                array(
306
                    'scheme'  => 'tcp',
307
                    'host'    => '127.0.0.1',
308
                    'port'    => 6379,
309
                    'timeout' => '2.0',
310
                )
311
            );
312
            try {
313
              $redis->connect();
314
              $isRedisAvailable = $redis->getConnection()->isConnected();
315
            } catch (\Exception $e) {
316
              // nothing
317
            }
318
          }
319
320
          if ($isRedisAvailable === false) {
321
            $redis = null;
322
          }
323
324
          $adapterRedis = new AdapterPredis($redis);
325
          if ($adapterRedis->installed() === true) {
326
327
            // -------------------------------------------------------------
328
            // Redis
329
            // -------------------------------------------------------------
330
            $adapter = $adapterRedis;
331
332
          } else {
333
334
            $adapterXcache = new AdapterXcache();
335
            if ($adapterXcache->installed() === true) {
336
337
              // -------------------------------------------------------------
338
              // "Xcache"
339
              // -------------------------------------------------------------
340
              $adapter = $adapterXcache;
341
342
            } else {
343
344
              $adapterApc = new AdapterApc();
345
              if ($adapterApc->installed() === true) {
346
347
                // -------------------------------------------------------------
348
                // "APC"
349
                // -------------------------------------------------------------
350
                $adapter = $adapterApc;
351
352
              } else {
353
354
                $adapterApcu = new AdapterApcu();
355
                if ($adapterApcu->installed() === true) {
356
357
                  // -------------------------------------------------------------
358
                  // "APCu"
359
                  // -------------------------------------------------------------
360
                  $adapter = $adapterApcu;
361
362
                } else {
363
364
                  $adapterFile = new AdapterFile();
365
                  if ($adapterFile->installed() === true) {
366
367
                    // -------------------------------------------------------------
368
                    // File-Cache
369
                    // -------------------------------------------------------------
370
                    $adapter = $adapterFile;
371
372
                  } else {
373
374
                    // -------------------------------------------------------------
375
                    // Static-PHP-Cache
376
                    // -------------------------------------------------------------
377
                    $adapter = new AdapterArray();
378
                  }
379
                }
380
              }
381
            }
382
          }
383
        }
384
      }
385
386
      // save to static cache
387
      $adapterCache = $adapter;
388
    }
389
390
    return $adapter;
391
  }
392
393
  /**
394
   * Set "isReady" state.
395
   *
396
   * @param boolean $isReady
397
   */
398 42
  private function setCacheIsReady($isReady)
399
  {
400 42
    $this->isReady = (boolean)$isReady;
401 42
  }
402
403
  /**
404
   * Get the "isReady" state.
405
   *
406
   * @return boolean
407
   */
408 4
  public function getCacheIsReady()
409
  {
410 4
    return $this->isReady;
411
  }
412
413
  /**
414
   * Get cached-item by key.
415
   *
416
   * @param string $key
417
   * @param int    $staticCacheHitCounter WARNING: This static cache has no TTL, it will be cleaned on the next request
418
   *                                      and it will use more memory as e.g. memcache.
419
   *
420
   * @return mixed
421
   */
422 19
  public function getItem($key, $staticCacheHitCounter = 0)
423
  {
424
    // init
425 19
    $staticCacheHitCounter = (int)$staticCacheHitCounter;
426
427 19
    static $STATIC_CACHE = array();
428 19
    static $STATIC_CACHE_COUNTER = array();;
429
430 19
    if ($this->adapter instanceof iAdapter) {
431 19
      $storeKey = $this->calculateStoreKey($key);
432
433
      // check if we already using static-cache
434 19
      if ($this->adapter instanceof AdapterArray) {
435 5
        $staticCacheHitCounter = 0;
436 5
      }
437
438 19
      if ($staticCacheHitCounter !== 0) {
439
        if (!isset($STATIC_CACHE_COUNTER[$storeKey])) {
440
          $STATIC_CACHE_COUNTER[$storeKey] = 0;
441
        }
442
443
        if ($STATIC_CACHE_COUNTER[$storeKey] < ($staticCacheHitCounter + 1)) {
444
          $STATIC_CACHE_COUNTER[$storeKey]++;
445
        }
446
447
        // get from static-cache
448
        if (array_key_exists($storeKey, $STATIC_CACHE) === true) {
449
          return $STATIC_CACHE[$storeKey];
450
        }
451
      }
452
453 19
      $serialized = $this->adapter->get($storeKey);
454 19
      $value = $serialized ? $this->serializer->unserialize($serialized) : null;
455
456
      if (
457
          $staticCacheHitCounter !== 0
458 19
          &&
459
          $STATIC_CACHE_COUNTER[$storeKey] >= $staticCacheHitCounter
460 19
      ) {
461
        // save into static-cache
462
        $STATIC_CACHE[$storeKey] = $value;
463
      }
464
465 19
    } else {
466
      return null;
467
    }
468
469 19
    return $value;
470
  }
471
472
  /**
473
   * Calculate store-key (prefix + $rawKey).
474
   *
475
   * @param string $rawKey
476
   *
477
   * @return string
478
   */
479 33
  private function calculateStoreKey($rawKey)
480
  {
481 33
    $str = $this->getPrefix() . $rawKey;
482
483 33
    if ($this->adapter instanceof AdapterFile) {
484 6
      $str = $this->cleanStoreKey($str);
485 6
    }
486
487 33
    return $str;
488
  }
489
490
  /**
491
   * Clean store-key (required e.g. for the "File"-Adapter).
492
   *
493
   * @param string $str
494
   *
495
   * @return string
496
   */
497 6
  private function cleanStoreKey($str)
498
  {
499 6
    $str = preg_replace("/[\r\n\t ]+/", ' ', $str);
500 6
    $str = str_replace(
501 6
        array('"', '*', ':', '<', '>', '?', "'", '|'),
502
        array(
503 6
            '-+-',
504 6
            '-+-+-',
505 6
            '-+-+-+-',
506 6
            '-+-+-+-+-',
507 6
            '-+-+-+-+-+-',
508 6
            '-+-+-+-+-+-+-',
509 6
            '-+-+-+-+-+-+-+-',
510 6
            '-+-+-+-+-+-+-+-+-',
511 6
        ),
512
        $str
513 6
    );
514 6
    $str = html_entity_decode($str, ENT_QUOTES, 'UTF-8');
515 6
    $str = htmlentities($str, ENT_QUOTES, 'UTF-8');
516 6
    $str = preg_replace('/(&)([a-z])([a-z]+;)/i', '$2', $str);
517 6
    $str = str_replace(' ', '-', $str);
518 6
    $str = rawurlencode($str);
519 6
    $str = str_replace('%', '-', $str);
520
521 6
    return $str;
522
  }
523
524
  /**
525
   * Get the prefix.
526
   *
527
   * @return string
528
   */
529 33
  public function getPrefix()
530
  {
531 33
    return $this->prefix;
532
  }
533
534
  /**
535
   * !!! Set the prefix. !!!
536
   *
537
   * WARNING: Do not use if you don't know what you do. Because this will overwrite the default prefix.
538
   *
539
   * @param string $prefix
540
   */
541 42
  public function setPrefix($prefix)
542
  {
543 42
    $this->prefix = (string)$prefix;
544 42
  }
545
546
  /**
547
   * Set cache-item by key => value + date.
548
   *
549
   * @param string    $key
550
   * @param mixed     $value
551
   * @param \DateTime $date
552
   *
553
   * @return boolean
554
   * @throws \Exception
555
   */
556 6
  public function setItemToDate($key, $value, \DateTime $date)
557
  {
558 6
    $ttl = $date->getTimestamp() - time();
559
560 6
    if ($ttl <= 0) {
561 1
      throw new \Exception('Date in the past.');
562
    }
563
564 5
    $storeKey = $this->calculateStoreKey($key);
565
566 5
    return $this->setItem($storeKey, $value, $ttl);
567
  }
568
569
  /**
570
   * Set cache-item by key => value + ttl.
571
   *
572
   * @param string $key
573
   * @param mixed  $value
574
   * @param int    $ttl
575
   *
576
   * @return bool
577
   */
578 18
  public function setItem($key, $value, $ttl = 0)
579
  {
580
    if (
581 18
        $this->adapter instanceof iAdapter
582 18
        &&
583 18
        $this->serializer instanceof iSerializer
584 18
    ) {
585 18
      $storeKey = $this->calculateStoreKey($key);
586 18
      $serialized = $this->serializer->serialize($value);
587
588 18
      if ($ttl) {
589 7
        return $this->adapter->setExpired($storeKey, $serialized, $ttl);
590
      } else {
591 11
        return $this->adapter->set($storeKey, $serialized);
592
      }
593
    } else {
594
      return false;
595
    }
596
  }
597
598
  /**
599
   * Remove a cached-item.
600
   *
601
   * @param string $key
602
   *
603
   * @return bool
604
   */
605 2 View Code Duplication
  public function removeItem($key)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in 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...
606
  {
607 2
    if ($this->adapter instanceof iAdapter) {
608 2
      $storeKey = $this->calculateStoreKey($key);
609
610 2
      return $this->adapter->remove($storeKey);
611
    } else {
612
      return false;
613
    }
614
  }
615
616
  /**
617
   * Remove all cached-items.
618
   *
619
   * @return bool
620
   */
621 1
  public function removeAll()
622
  {
623 1
    if ($this->adapter instanceof iAdapter) {
624 1
      return $this->adapter->removeAll();
625
    } else {
626
      return false;
627
    }
628
  }
629
630
  /**
631
   * Check if cached-item exists.
632
   *
633
   * @param string $key
634
   *
635
   * @return boolean
636
   */
637 6 View Code Duplication
  public function existsItem($key)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in 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...
638
  {
639 6
    if ($this->adapter instanceof iAdapter) {
640 6
      $storeKey = $this->calculateStoreKey($key);
641
642 6
      return $this->adapter->exists($storeKey);
643
    } else {
644
      return false;
645
    }
646
  }
647
648
  /**
649
   * Get the current adapter class-name.
650
   *
651
   * @return string
652
   */
653 2
  public function getUsedAdapterClassName()
654
  {
655 2
    return get_class($this->adapter);
656
  }
657
658
  /**
659
   * Get the current serializer class-name.
660
   *
661
   * @return string
662
   */
663 2
  public function getUsedSerializerClassName()
664
  {
665 2
    return get_class($this->serializer);
666
  }
667
}
668