856e0b2f3279e20e24fe24cd5b8a940e07d31bab
[Packages/TYPO3.CMS.git] / typo3 / sysext / core / Tests / Unit / Cache / Backend / PdoBackendTest.php
1 <?php
2 namespace TYPO3\CMS\Core\Tests\Unit\Cache\Backend;
3
4 /*
5 * This file is part of the TYPO3 CMS project.
6 *
7 * It is free software; you can redistribute it and/or modify it under
8 * the terms of the GNU General Public License, either version 2
9 * of the License, or any later version.
10 *
11 * For the full copyright and license information, please read the
12 * LICENSE.txt file that was distributed with this source code.
13 *
14 * The TYPO3 project - inspiring people to share!
15 */
16
17 /**
18 * Testcase for the PDO cache backend
19 */
20 class PdoBackendTest extends \TYPO3\TestingFramework\Core\Unit\UnitTestCase
21 {
22 /**
23 * Subject is not notice free, disable E_NOTICES
24 */
25 protected static $suppressNotices = true;
26
27 /**
28 * Sets up this testcase
29 */
30 protected function setUp()
31 {
32 if (!extension_loaded('pdo_sqlite')) {
33 $this->markTestSkipped('pdo_sqlite extension was not available');
34 }
35 }
36
37 /**
38 * @test
39 */
40 public function setThrowsExceptionIfNoFrontEndHasBeenSet()
41 {
42 $this->expectException(\TYPO3\CMS\Core\Cache\Exception::class);
43 $this->expectExceptionCode(1259515600);
44
45 $backend = new \TYPO3\CMS\Core\Cache\Backend\PdoBackend('Testing');
46 $data = 'Some data';
47 $identifier = 'MyIdentifier';
48 $backend->set($identifier, $data);
49 }
50
51 /**
52 * @test
53 */
54 public function itIsPossibleToSetAndCheckExistenceInCache()
55 {
56 $backend = $this->setUpBackend();
57 $data = 'Some data';
58 $identifier = 'MyIdentifier';
59 $backend->set($identifier, $data);
60 $this->assertTrue($backend->has($identifier));
61 }
62
63 /**
64 * @test
65 */
66 public function itIsPossibleToSetAndGetEntry()
67 {
68 $backend = $this->setUpBackend();
69 $data = 'Some data';
70 $identifier = 'MyIdentifier';
71 $backend->set($identifier, $data);
72 $fetchedData = $backend->get($identifier);
73 $this->assertEquals($data, $fetchedData);
74 }
75
76 /**
77 * @test
78 */
79 public function itIsPossibleToRemoveEntryFromCache()
80 {
81 $backend = $this->setUpBackend();
82 $data = 'Some data';
83 $identifier = 'MyIdentifier';
84 $backend->set($identifier, $data);
85 $backend->remove($identifier);
86 $this->assertFalse($backend->has($identifier));
87 }
88
89 /**
90 * @test
91 */
92 public function itIsPossibleToOverwriteAnEntryInTheCache()
93 {
94 $backend = $this->setUpBackend();
95 $data = 'Some data';
96 $identifier = 'MyIdentifier';
97 $backend->set($identifier, $data);
98 $otherData = 'some other data';
99 $backend->set($identifier, $otherData);
100 $fetchedData = $backend->get($identifier);
101 $this->assertEquals($otherData, $fetchedData);
102 }
103
104 /**
105 * @test
106 */
107 public function findIdentifiersByTagFindsSetEntries()
108 {
109 $backend = $this->setUpBackend();
110 $data = 'Some data';
111 $entryIdentifier = 'MyIdentifier';
112 $backend->set($entryIdentifier, $data, ['UnitTestTag%tag1', 'UnitTestTag%tag2']);
113 $retrieved = $backend->findIdentifiersByTag('UnitTestTag%tag1');
114 $this->assertEquals($entryIdentifier, $retrieved[0]);
115 $retrieved = $backend->findIdentifiersByTag('UnitTestTag%tag2');
116 $this->assertEquals($entryIdentifier, $retrieved[0]);
117 }
118
119 /**
120 * @test
121 */
122 public function setRemovesTagsFromPreviousSet()
123 {
124 $backend = $this->setUpBackend();
125 $data = 'Some data';
126 $entryIdentifier = 'MyIdentifier';
127 $backend->set($entryIdentifier, $data, ['UnitTestTag%tag1', 'UnitTestTag%tag2']);
128 $backend->set($entryIdentifier, $data, ['UnitTestTag%tag3']);
129 $retrieved = $backend->findIdentifiersByTag('UnitTestTag%tag2');
130 $this->assertEquals([], $retrieved);
131 }
132
133 /**
134 * @test
135 */
136 public function setOverwritesExistingEntryThatExceededItsLifetimeWithNewData()
137 {
138 $backend = $this->setUpBackend();
139 $data1 = 'data1';
140 $entryIdentifier = $this->getUniqueId('test');
141 $backend->set($entryIdentifier, $data1, [], 1);
142 $data2 = 'data2';
143 $GLOBALS['EXEC_TIME'] += 2;
144 $backend->set($entryIdentifier, $data2, [], 10);
145 $this->assertEquals($data2, $backend->get($entryIdentifier));
146 }
147
148 /**
149 * @test
150 */
151 public function hasReturnsFalseIfTheEntryDoesntExist()
152 {
153 $backend = $this->setUpBackend();
154 $identifier = 'NonExistingIdentifier';
155 $this->assertFalse($backend->has($identifier));
156 }
157
158 /**
159 * @test
160 */
161 public function removeReturnsFalseIfTheEntryDoesntExist()
162 {
163 $backend = $this->setUpBackend();
164 $identifier = 'NonExistingIdentifier';
165 $this->assertFalse($backend->remove($identifier));
166 }
167
168 /**
169 * @test
170 */
171 public function flushByTagRemovesCacheEntriesWithSpecifiedTag()
172 {
173 $backend = $this->setUpBackend();
174 $data = 'some data' . microtime();
175 $backend->set('PdoBackendTest1', $data, ['UnitTestTag%test', 'UnitTestTag%boring']);
176 $backend->set('PdoBackendTest2', $data, ['UnitTestTag%test', 'UnitTestTag%special']);
177 $backend->set('PdoBackendTest3', $data, ['UnitTestTag%test']);
178 $backend->flushByTag('UnitTestTag%special');
179 $this->assertTrue($backend->has('PdoBackendTest1'), 'PdoBackendTest1');
180 $this->assertFalse($backend->has('PdoBackendTest2'), 'PdoBackendTest2');
181 $this->assertTrue($backend->has('PdoBackendTest3'), 'PdoBackendTest3');
182 }
183
184 /**
185 * @test
186 */
187 public function flushByTagsRemovesCacheEntriesWithSpecifiedTags()
188 {
189 $backend = $this->setUpBackend();
190 $data = 'some data' . microtime();
191 $backend->set('PdoBackendTest1', $data, ['UnitTestTag%test', 'UnitTestTags%boring']);
192 $backend->set('PdoBackendTest2', $data, ['UnitTestTag%test', 'UnitTestTag%special']);
193 $backend->set('PdoBackendTest3', $data, ['UnitTestTag%test']);
194 $backend->flushByTags(['UnitTestTag%special', 'UnitTestTags%boring']);
195 $this->assertFalse($backend->has('PdoBackendTest1'), 'PdoBackendTest1');
196 $this->assertFalse($backend->has('PdoBackendTest2'), 'PdoBackendTest2');
197 $this->assertTrue($backend->has('PdoBackendTest3'), 'PdoBackendTest3');
198 }
199
200 /**
201 * @test
202 */
203 public function flushRemovesAllCacheEntries()
204 {
205 $backend = $this->setUpBackend();
206 $data = 'some data' . microtime();
207 $backend->set('PdoBackendTest1', $data);
208 $backend->set('PdoBackendTest2', $data);
209 $backend->set('PdoBackendTest3', $data);
210 $backend->flush();
211 $this->assertFalse($backend->has('PdoBackendTest1'), 'PdoBackendTest1');
212 $this->assertFalse($backend->has('PdoBackendTest2'), 'PdoBackendTest2');
213 $this->assertFalse($backend->has('PdoBackendTest3'), 'PdoBackendTest3');
214 }
215
216 /**
217 * @test
218 */
219 public function flushRemovesOnlyOwnEntries()
220 {
221 $thisCache = $this->createMock(\TYPO3\CMS\Core\Cache\Frontend\FrontendInterface::class);
222 $thisCache->expects($this->any())->method('getIdentifier')->will($this->returnValue('thisCache'));
223 $thisBackend = $this->setUpBackend();
224 $thisBackend->setCache($thisCache);
225 $thatCache = $this->createMock(\TYPO3\CMS\Core\Cache\Frontend\FrontendInterface::class);
226 $thatCache->expects($this->any())->method('getIdentifier')->will($this->returnValue('thatCache'));
227 $thatBackend = $this->setUpBackend();
228 $thatBackend->setCache($thatCache);
229 $thisBackend->set('thisEntry', 'Hello');
230 $thatBackend->set('thatEntry', 'World!');
231 $thatBackend->flush();
232 $this->assertEquals('Hello', $thisBackend->get('thisEntry'));
233 $this->assertFalse($thatBackend->has('thatEntry'));
234 }
235
236 /**
237 * @test
238 */
239 public function collectGarbageReallyRemovesAnExpiredCacheEntry()
240 {
241 $backend = $this->setUpBackend();
242 $data = 'some data' . microtime();
243 $entryIdentifier = 'BackendPDORemovalTest';
244 $backend->set($entryIdentifier, $data, [], 1);
245 $this->assertTrue($backend->has($entryIdentifier));
246 $GLOBALS['EXEC_TIME'] += 2;
247 $backend->collectGarbage();
248 $this->assertFalse($backend->has($entryIdentifier));
249 }
250
251 /**
252 * @test
253 */
254 public function collectGarbageReallyRemovesAllExpiredCacheEntries()
255 {
256 $backend = $this->setUpBackend();
257 $data = 'some data' . microtime();
258 $entryIdentifier = 'BackendPDORemovalTest';
259 $backend->set($entryIdentifier . 'A', $data, [], null);
260 $backend->set($entryIdentifier . 'B', $data, [], 10);
261 $backend->set($entryIdentifier . 'C', $data, [], 1);
262 $backend->set($entryIdentifier . 'D', $data, [], 1);
263 $this->assertTrue($backend->has($entryIdentifier . 'A'));
264 $this->assertTrue($backend->has($entryIdentifier . 'B'));
265 $this->assertTrue($backend->has($entryIdentifier . 'C'));
266 $this->assertTrue($backend->has($entryIdentifier . 'D'));
267 $GLOBALS['EXEC_TIME'] += 2;
268 $backend->collectGarbage();
269 $this->assertTrue($backend->has($entryIdentifier . 'A'));
270 $this->assertTrue($backend->has($entryIdentifier . 'B'));
271 $this->assertFalse($backend->has($entryIdentifier . 'C'));
272 $this->assertFalse($backend->has($entryIdentifier . 'D'));
273 }
274
275 /**
276 * Sets up the PDO backend used for testing
277 *
278 * @return \TYPO3\CMS\Core\Cache\Backend\PdoBackend
279 */
280 protected function setUpBackend()
281 {
282 $mockCache = $this->createMock(\TYPO3\CMS\Core\Cache\Frontend\FrontendInterface::class);
283 $mockCache->expects($this->any())->method('getIdentifier')->will($this->returnValue('TestCache'));
284 $backend = \TYPO3\CMS\Core\Utility\GeneralUtility::makeInstance(\TYPO3\CMS\Core\Cache\Backend\PdoBackend::class, 'Testing');
285 $backend->setCache($mockCache);
286 $backend->setDataSourceName('sqlite::memory:');
287 $backend->initializeObject();
288 return $backend;
289 }
290 }