Skip to content

Commit 7b9b92c

Browse files
committed
Make sure hierarchy works
1 parent f64d2e5 commit 7b9b92c

File tree

5 files changed

+124
-22
lines changed

5 files changed

+124
-22
lines changed

README.md

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -16,8 +16,7 @@ for ($i = 0; $i < 100; $i++) {
1616

1717
$pool->hasItem('|users|4711|followers|12|likes'); // True
1818

19-
$item = $pool->getItem('|users|4711|followers');
20-
$pool->deleteItem($item);
19+
$pool->deleteItem('|users|4711|followers');
2120

2221
$pool->hasItem('|users|4711|followers|12|likes'); // False
2322
```

src/HierarchicalCachePool.php

Lines changed: 71 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,9 @@
1111

1212
namespace Cache\Hierarchy;
1313

14+
use Cache\Adapter\Common\CacheItem;
1415
use Cache\Adapter\Common\Exception\InvalidArgumentException;
16+
use Cache\Taggable\TaggableItemInterface;
1517
use Cache\Taggable\TaggablePoolInterface;
1618
use Psr\Cache\CacheItemInterface;
1719
use Psr\Cache\CacheItemPoolInterface;
@@ -42,11 +44,23 @@ public function __construct(CacheItemPoolInterface $cache)
4244
*/
4345
public function getItem($key, array $tags = [])
4446
{
45-
if (!$this->isHierarchyKey($key)) {
46-
return $this->cache->getItem($key, $tags);
47+
$item = $this->cache->getItem($key, $tags);
48+
if (!$this->isHierarchyKey($key) || !$item->isHit()) {
49+
return $item;
4750
}
4851

49-
// TODO: Implement getItem() method.
52+
if (!$this->validateParents($key, $tags)) {
53+
return $item;
54+
}
55+
56+
// Invalid item
57+
if ($item instanceof TaggableItemInterface) {
58+
$key = $item->getTaggedKey();
59+
} else {
60+
$key = $item->getKey();
61+
}
62+
63+
return new CacheItem($key);
5064
}
5165

5266
/**
@@ -67,10 +81,12 @@ public function getItems(array $keys = [], array $tags = [])
6781
*/
6882
public function hasItem($key, array $tags = [])
6983
{
70-
if (!$this->isHierarchyKey($key)) {
71-
return $this->cache->hasItem($key, $tags);
84+
$hasItem = $this->cache->hasItem($key, $tags);
85+
if (!$this->isHierarchyKey($key) || $hasItem === false) {
86+
return $hasItem;
7287
}
73-
// TODO: Implement hasItem() method.
88+
89+
return $this->validateParents($key, $tags);
7490
}
7591

7692
/**
@@ -86,30 +102,31 @@ public function clear(array $tags = [])
86102
*/
87103
public function deleteItem($key, array $tags = [])
88104
{
89-
if (!$this->isHierarchyKey($key)) {
90-
return $this->cache->deleteItem($key, $tags);
91-
}
92-
// TODO: Implement deleteItem() method.
105+
return $this->cache->deleteItem($key, $tags);
93106
}
94107

95108
/**
96109
* {@inheritdoc}
97110
*/
98111
public function deleteItems(array $keys, array $tags = [])
99112
{
100-
$result = true;
101-
foreach ($keys as $key) {
102-
$result = $result && $this->deleteItem($key, $tags);
103-
}
104-
105-
return $result;
113+
return $this->cache->deleteItems($keys, $tags);
106114
}
107115

108116
/**
109117
* {@inheritdoc}
110118
*/
111119
public function save(CacheItemInterface $item)
112120
{
121+
$parts = $this->explodeKey($item->getKey());
122+
$parentKey = '';
123+
foreach ($parts as $part) {
124+
$parentKey .= $part;
125+
$parent = $this->cache->getItem($parentKey);
126+
$parent->set(null);
127+
$this->cache->save($parent);
128+
}
129+
113130
return $this->cache->save($item);
114131
}
115132

@@ -143,4 +160,42 @@ private function isHierarchyKey($key)
143160

144161
return substr($key, 0, 1) === self::SEPARATOR;
145162
}
163+
164+
/**
165+
* @param string $key
166+
* @param array $tags
167+
*
168+
* @return bool true if parents are valid
169+
*/
170+
private function validateParents($key, array $tags)
171+
{
172+
$parts = $this->explodeKey($key);
173+
$parentKey = '';
174+
foreach ($parts as $part) {
175+
$parentKey .= $part;
176+
if (!$this->cache->hasItem($parentKey, $tags)) {
177+
// Invalid item
178+
return false;
179+
}
180+
}
181+
182+
return true;
183+
}
184+
185+
/**
186+
* @param CacheItemInterface $item
187+
*
188+
* @return array
189+
*/
190+
private function explodeKey($key)
191+
{
192+
$parts = explode(self::SEPARATOR, $key);
193+
194+
unset($parts[0]);
195+
foreach ($parts as &$part) {
196+
$part = self::SEPARATOR.$part;
197+
}
198+
199+
return $parts;
200+
}
146201
}
Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,50 @@
1+
<?php
2+
3+
/*
4+
* This file is part of php-cache\apc-adapter package.
5+
*
6+
* (c) 2015-2015 Aaron Scherer <[email protected]>, Tobias Nyholm <[email protected]>
7+
*
8+
* This source file is subject to the MIT license that is bundled
9+
* with this source code in the file LICENSE.
10+
*/
11+
12+
namespace Cache\Hierarchy;
13+
14+
use Cache\Adapter\Apc\ApcCachePool;
15+
use Cache\Adapter\PHPArray\ArrayCachePool;
16+
use Cache\IntegrationTests\CachePoolTest as BaseTest;
17+
18+
class HierarchicalCachePoolTest extends \PHPUnit_Framework_TestCase
19+
{
20+
private $cache;
21+
22+
public function createCachePool()
23+
{
24+
return new HierarchicalCachePool($this->getCache());
25+
}
26+
27+
public function getCache()
28+
{
29+
if ($this->cache === null) {
30+
$this->cache = new ArrayCachePool();
31+
}
32+
33+
return $this->cache;
34+
}
35+
36+
public function testBasicUsage()
37+
{
38+
$pool = $this->createCachePool();
39+
$user = 4711;
40+
for ($i = 0; $i < 10; $i++) {
41+
$item = $pool->getItem(sprintf('|users|%d|followers|%d|likes', $user, $i));
42+
$item->set('Justin Bieber');
43+
$pool->save($item);
44+
}
45+
46+
$this->assertTrue($pool->hasItem('|users|4711|followers|4|likes'));
47+
$pool->deleteItem('|users|4711|followers');
48+
$this->assertFalse($pool->hasItem('|users|4711|followers|4|likes'));
49+
}
50+
}

tests/IntegrationPoolTest.php

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -11,11 +11,10 @@
1111

1212
namespace Cache\Hierarchy;
1313

14-
use Cache\Adapter\Apc\ApcCachePool;
1514
use Cache\Adapter\PHPArray\ArrayCachePool;
16-
use Cache\IntegrationTests\CachePoolTest as BaseTest;
15+
use Cache\IntegrationTests\CachePoolTest;
1716

18-
class IntegrationPoolTest extends BaseTest
17+
class IntegrationPoolTest extends CachePoolTest
1918
{
2019
private $cache;
2120

tests/IntegrationTagTest.php

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,6 @@
1111

1212
namespace Cache\Hierarchy;
1313

14-
use Cache\Adapter\Apc\ApcCachePool;
1514
use Cache\Adapter\PHPArray\ArrayCachePool;
1615
use Cache\IntegrationTests\TaggableCachePoolTest;
1716

0 commit comments

Comments
 (0)