ILIAS  trunk Revision v11.0_alpha-2638-g80c1d007f79
CacheTest.php
Go to the documentation of this file.
1 <?php
2 
19 namespace ILIAS\Cache;
20 
33 
34 require_once(__DIR__ . '/../../../../vendor/composer/vendor/autoload.php');
35 
39 class CacheTest extends TestCase
40 {
41  public const TEST_CONTAINER = 'test_container';
45  private \ilLanguage $language_mock;
46  private Factory $refinery;
47 
48  protected function setUp(): void
49  {
50  $this->language_mock = $this->createMock(\ilLanguage::class);
51  $this->refinery = new Factory(
52  new \ILIAS\Data\Factory(),
53  $this->language_mock
54  );
55  // prevent chached values between tests
56  $static_flush = new PHPStatic($this->getConfig(Config::PHPSTATIC));
57  $static_flush->flush();
58  }
59 
63  protected function getConfig(string $adaptor_name = Config::PHPSTATIC): Config
64  {
65  return new Config(
66  $adaptor_name,
67  true,
68  [self::TEST_CONTAINER],
69  new class () extends NullNodeRepository {
70  public function getNodes(): array
71  {
72  return [new Node('127.0.0.1', 11211, 100)];
73  }
74  }
75  );
76  }
77 
78  public function testActivatedComponents(): void
79  {
80  $config = new Config(
82  true,
83  ['one', 'two']
84  );
85 
86  $services = new Services($config);
87  $this->assertInstanceOf(ActiveContainer::class, $services->get($this->getDummyRequest('one')));
88  $this->assertInstanceOf(ActiveContainer::class, $services->get($this->getDummyRequest('two')));
89  $this->assertInstanceOf(VoidContainer::class, $services->get($this->getDummyRequest('three')));
90 
91  $config = new Config(
93  true,
94  ['*']
95  );
96  $services = new Services($config);
97  $this->assertInstanceOf(ActiveContainer::class, $services->get($this->getDummyRequest('one')));
98  $this->assertInstanceOf(ActiveContainer::class, $services->get($this->getDummyRequest('two')));
99  $this->assertInstanceOf(ActiveContainer::class, $services->get($this->getDummyRequest('three')));
100  }
101 
102  public function testMultipleContainers(): void
103  {
104  $config = new Config(
106  true,
107  ['one', 'two']
108  );
109 
110  $services = new Services($config);
111 
112  $one = $this->getDummyRequest('one');
113  $two = $this->getDummyRequest('two');
114  $three = $this->getDummyRequest('three');
115 
116  $this->assertEquals('one', $one->getContainerKey());
117  $this->assertEquals('two', $two->getContainerKey());
118  $this->assertEquals('three', $three->getContainerKey());
119 
120  $container_one = $services->get($one);
121  $container_two = $services->get($two);
122  $container_three = $services->get($three);
123 
124  $this->assertInstanceOf(ActiveContainer::class, $container_one);
125  $this->assertInstanceOf(ActiveContainer::class, $container_two);
126  $this->assertInstanceOf(VoidContainer::class, $container_three);
127 
128  $container_one->set('test', 'test_value');
129  $this->assertTrue($container_one->has('test'));
130  $this->assertEquals('test_value', $container_one->get('test', $this->refinery->to()->string()));
131 
132  $container_two->set('test', 'test_value');
133  $this->assertTrue($container_two->has('test'));
134  $this->assertEquals('test_value', $container_two->get('test', $this->refinery->to()->string()));
135 
136  $container_three->set('test', 'test_value');
137  $this->assertFalse($container_three->has('test'));
138  $this->assertNull($container_three->get('test', $this->refinery->to()->string()));
139  }
140 
141  public function testLock(): void
142  {
143  $services = new Services($this->getConfig());
144  $container = $services->get($this->getDummyRequest(self::TEST_CONTAINER));
145  $container->unlock();
146 
147  $container->set('test', 'test_value');
148  $this->assertTrue($container->has('test'));
149  $this->assertEquals('test_value', $container->get('test', $this->refinery->to()->string()));
150 
151  $container->lock(1 / 1000);
152  $this->assertTrue($container->isLocked());
153  $this->assertFalse($container->has('test'));
154  $this->assertNull($container->get('test', $this->refinery->to()->string()));
155  usleep(1000);
156  $this->assertFalse($container->isLocked());
157  $this->assertTrue($container->has('test'));
158  $this->assertEquals('test_value', $container->get('test', $this->refinery->to()->string()));
159 
160  // Second Run
161  $container->lock(1 / 1000);
162  $this->assertTrue($container->isLocked());
163  $this->assertFalse($container->has('test'));
164  $this->assertNull($container->get('test', $this->refinery->to()->string()));
165  usleep(100);
166  $this->assertTrue($container->isLocked());
167  $this->assertFalse($container->has('test'));
168  $this->assertNull($container->get('test', $this->refinery->to()->string()));
169 
170  usleep(5000); // to avoid problems with the next test
171  $this->assertFalse($container->isLocked());
172  }
173 
174  public static function getInvalidLockTimes(): array
175  {
176  return [
177  [-10],
178  [-1],
179  [301],
180  [300.1],
181  ];
182  }
183 
184  #[DataProvider('getInvalidLockTimes')]
185  public function testInvalidLockTimes(float|int $time): void
186  {
187  $services = new Services($this->getConfig());
188  $container = $services->get($this->getDummyRequest(self::TEST_CONTAINER));
189  $this->expectException(\InvalidArgumentException::class);
190  $container->lock($time);
191  }
192 
193  public function testDelete(): void
194  {
195  $services = new Services($this->getConfig());
196  $container = $services->get($this->getDummyRequest(self::TEST_CONTAINER));
197 
198  $container->set('test', 'test_value');
199  $this->assertTrue($container->has('test'));
200  $this->assertEquals('test_value', $container->get('test', $this->refinery->to()->string()));
201 
202  $container->delete('test');
203  $this->assertFalse($container->has('test'));
204  $this->assertNull($container->get('test', $this->refinery->to()->string()));
205  }
206 
207  public function testDefaultAdaptor(): void
208  {
209  $request = $this->getDummyRequest(self::TEST_CONTAINER);
210 
211  $to_string = $this->refinery->kindlyTo()->string();
212 
213  $config = $this->getConfig();
214 
215  $static = new PHPStatic($config);
216  $this->assertTrue($static->isAvailable());
217 
218  $services = new Services($config);
219  $container = $services->get($request);
220  $this->assertInstanceOf(ActiveContainer::class, $container);
221  $this->assertEquals(Config::PHPSTATIC, $container->getAdaptorName());
222  $this->assertEquals(self::TEST_CONTAINER, $container->getContainerName());
223 
224  $this->assertFalse($container->has('test'));
225  $container->set('test', 'test_value');
226  $this->assertTrue($container->has('test'));
227  $this->assertEquals('test_value', $container->get('test', $to_string));
228  $container->delete('test');
229  $this->assertFalse($container->has('test'));
230 
231  $container->set('test2', 'test_value2');
232  $container->set('test3', 'test_value3');
233  $this->assertTrue($container->has('test2'));
234  $this->assertTrue($container->has('test3'));
235 
236  $container->flush();
237 
238  $this->assertFalse($container->has('test2'));
239  $this->assertFalse($container->has('test3'));
240  }
241 
242  public function testFlush(): void
243  {
244  $services = new Services($this->getConfig());
245  $container = $services->get($this->getDummyRequest(self::TEST_CONTAINER));
246 
247  $container->set('test', 'test_value');
248  $this->assertTrue($container->has('test'));
249  $this->assertEquals('test_value', $container->get('test', $this->refinery->to()->string()));
250 
251  $container->flush();
252  $this->assertFalse($container->has('test'));
253  $this->assertNull($container->get('test', $this->refinery->to()->string()));
254 
255  $container->set('test', 'test_value');
256  $this->assertTrue($container->has('test'));
257  $this->assertEquals('test_value', $container->get('test', $this->refinery->to()->string()));
258 
259  $services->flushAdapter();
260  $this->assertFalse($container->has('test'));
261  $this->assertNull($container->get('test', $this->refinery->to()->string()));
262  }
263 
264  public function testAPCAdapter(): void
265  {
266  $config = $this->getConfig(Config::APCU);
267  $services = new Services($config);
268  $container = $services->get($this->getDummyRequest(self::TEST_CONTAINER));
269  $this->assertEquals(Config::APCU, $container->getAdaptorName());
270  $this->assertEquals(self::TEST_CONTAINER, $container->getContainerName());
271 
272  $apcu = new APCu($config);
273  if (!$apcu->isAvailable() || !(bool) ini_get('apc.enable_cli')) {
274  $this->markTestSkipped('APCu is not available or not enabled for CLI');
275  }
276 
277  $to_string = $this->refinery->kindlyTo()->string();
278 
279  $this->assertFalse($container->has('test'));
280  $container->set('test', 'test_value');
281  $this->assertTrue($container->has('test'));
282  $this->assertEquals('test_value', $container->get('test', $to_string));
283  $container->delete('test');
284  $this->assertFalse($container->has('test'));
285 
286  $container->set('test2', 'test_value2');
287  $container->set('test3', 'test_value3');
288  $this->assertTrue($container->has('test2'));
289  $this->assertTrue($container->has('test3'));
290 
291  $container->flush();
292 
293  $this->assertFalse($container->has('test2'));
294  $this->assertFalse($container->has('test3'));
295  }
296 
301  private function deactivatedTestMemcachedAdapter(): void
302  {
303  $config = $this->getConfig(Config::MEMCACHED);
304  $services = new Services($config);
305  $container = $services->get($this->getDummyRequest(self::TEST_CONTAINER));
306  $this->assertEquals(Config::MEMCACHED, $container->getAdaptorName());
307  $this->assertEquals(self::TEST_CONTAINER, $container->getContainerName());
308 
309  $apcu = new Memcached($config);
310  if (!$apcu->isAvailable()) {
311  $this->markTestSkipped('Memcached is not available');
312  }
313 
314  $this->assertFalse($container->has('test'));
315  $container->set('test', 'test_value');
316  $this->assertTrue($container->has('test'));
317  $this->assertEquals('test_value', $container->get('test'));
318  $container->delete('test');
319  $this->assertFalse($container->has('test'));
320 
321  $container->set('test2', 'test_value2');
322  $container->set('test3', 'test_value3');
323  $this->assertTrue($container->has('test2'));
324  $this->assertTrue($container->has('test3'));
325 
326  $container->flush();
327 
328  $this->assertFalse($container->has('test2'));
329  $this->assertFalse($container->has('test3'));
330  }
331 
332  public function testObjectStorage(): void
333  {
334  $services = new Services($this->getConfig());
335  $container = $services->get($this->getDummyRequest(self::TEST_CONTAINER));
336 
337  $first_object = new \stdClass();
338  $first_object->test = 'test';
339  $container->set('first_object', serialize($first_object));
340 
341  $this->assertTrue($container->has('first_object'));
342 
343  $to_string = $this->refinery->kindlyTo()->string();
344 
345  $data = $container->get('first_object', $to_string);
346  $first_object_from_cache = unserialize($data, ['allowed_classes' => [\stdClass::class]]);
347  $this->assertInstanceOf(\stdClass::class, $first_object_from_cache);
348  $this->assertEquals($first_object, $first_object_from_cache);
349  }
350 
351  public function testTypes(): void
352  {
353  $services = new Services($this->getConfig());
354  $container = $services->get($this->getDummyRequest(self::TEST_CONTAINER));
355 
356  // TRANSFORMATION
357  $to_string = $this->refinery->to()->string();
358  $to_int = $this->refinery->to()->int();
359  $to_array = $this->refinery->to()->listOf($to_string);
360  $to_bool = $this->refinery->to()->bool();
361 
362  // STRING
363  $string = 'test';
364  $container->set('string', $string);
365  $this->assertTrue($container->has('string'));
366  $string_from_cache = $container->get('string', $to_string);
367  $this->assertEquals($string, $string_from_cache);
368  $this->assertEquals(null, $container->get('string', $to_int));
369  $this->assertEquals(null, $container->get('string', $to_bool));
370  $this->assertEquals(null, $container->get('string', $to_array));
371  $this->assertIsString($string_from_cache);
372 
373  // ARRAY
374  $array = ['test', 'test2', 'test3'];
375  $container->set('array', $array);
376  $this->assertTrue($container->has('array'));
377  $array_from_cache = $container->get('array', $to_array);
378  $this->assertEquals($array, $array_from_cache);
379  $this->assertEquals(null, $container->get('array', $to_int));
380  $this->assertEquals(null, $container->get('array', $to_bool));
381  $this->assertEquals(null, $container->get('array', $to_string));
382  $this->assertIsArray($array_from_cache);
383 
384  // BOOL
385  $bool = true;
386  $container->set('bool', $bool);
387  $this->assertTrue($container->has('bool'));
388  $bool_from_cache = $container->get('bool', $to_bool);
389  $this->assertEquals($bool, $bool_from_cache);
390  $this->assertEquals(null, $container->get('bool', $to_int));
391  $this->assertEquals(null, $container->get('bool', $to_array));
392  $this->assertEquals(null, $container->get('bool', $to_string));
393  $this->assertIsBool($bool_from_cache);
394 
395  // ARRAY Different values
396  $array_with_different_values = ['test' => true, 'test2' => 123, 'test3' => ['test' => 'test'], 'test4' => null];
397  $container->set('array_with_different_values', $array_with_different_values);
398  $this->assertTrue($container->has('array_with_different_values'));
399 
400  $trafo = $this->refinery->to()->dictOf(
401  $this->refinery->custom()->transformation(
402  fn($value) => $value
403  )
404  );
405 
406  $array_with_different_values_from_cache = $container->get('array_with_different_values', $trafo);
407  $this->assertEquals($array_with_different_values, $array_with_different_values_from_cache);
408  $this->assertIsArray($array_with_different_values_from_cache);
409  $this->assertIsBool($array_with_different_values_from_cache['test']);
410  $this->assertIsInt($array_with_different_values_from_cache['test2']);
411  $this->assertIsArray($array_with_different_values_from_cache['test3']);
412  $this->assertNull($array_with_different_values_from_cache['test4']);
413 
414  $this->assertEquals(null, $container->get('array_with_different_values', $to_int));
415  $this->assertEquals(null, $container->get('array_with_different_values', $to_bool));
416  $this->assertEquals(null, $container->get('array_with_different_values', $to_string));
417 
418  // INT
419  $int = 123;
420  $container->set('int', $int);
421  $this->assertTrue($container->has('int'));
422  $int_from_cache = $container->get('int', $to_int);
423  $this->assertEquals($int, $int_from_cache);
424  $this->assertEquals(null, $container->get('int', $to_string));
425  $this->assertEquals(null, $container->get('int', $to_bool));
426  $this->assertEquals(null, $container->get('int', $to_array));
427  $this->assertIsInt($int_from_cache);
428  }
429 
430  public function testIncomatibleType(): void
431  {
432  $services = new Services($this->getConfig());
433  $container = $services->get(
434  $this->getDummyRequest(self::TEST_CONTAINER)
435  );
436 
437  $this->expectException(\TypeError::class);
438  $container->set('test', new \stdClass());
439  }
440 
441  public function testIncomatibleNestedType(): void
442  {
443  $services = new Services($this->getConfig());
444  $container = $services->get(
445  $this->getDummyRequest(self::TEST_CONTAINER)
446  );
447  $array_with_incompatible_type_in_it = [
448  'test' => 'test',
449  'test2' => 'test2',
450  'test3' => ['test' => new \stdClass()]
451  ];
452  $this->expectException(\InvalidArgumentException::class);
453  $container->set(
454  'array_with_incompatible_type_in_it',
455  $array_with_incompatible_type_in_it
456  );
457  }
458 
459  public function testIncomatibleTypeNested(): void
460  {
461  $services = new Services($this->getConfig());
462  $container = $services->get($this->getDummyRequest(self::TEST_CONTAINER));
463 
464  $array_with_incompatible_type_in_it = [
465  'test' => 'test',
466  'test2' => 'test2',
467  'test3' => ['test' => new \stdClass()]
468  ];
469  $this->expectException(\InvalidArgumentException::class);
470  $container->set('array_with_incompatible_type_in_it', $array_with_incompatible_type_in_it);
471  }
472 
473  protected function getDummyRequest(string $container_key): Request
474  {
475  return new BaseRequest($container_key);
476  }
477 }
deactivatedTestMemcachedAdapter()
this test cannot be executed in the CI on github sincewe do not have a memcached server there...
Definition: CacheTest.php:301
Interface Observer Contains several chained tasks and infos about them.
$container
Definition: wac.php:36
This file is part of ILIAS, a powerful learning management system published by ILIAS open source e-Le...
while($session_entry=$r->fetchRow(ilDBConstants::FETCHMODE_ASSOC)) return null
getConfig(string $adaptor_name=Config::PHPSTATIC)
Definition: CacheTest.php:63
ilLanguage $language_mock
Definition: CacheTest.php:45
testInvalidLockTimes(float|int $time)
Definition: CacheTest.php:185
getDummyRequest(string $container_key)
Definition: CacheTest.php:473
static getInvalidLockTimes()
Definition: CacheTest.php:174