Completed
Push — reduce_cache_tags ( 8b6ee4 )
by André
19:52
created

AbstractCacheHandlerTest::testUnCachedMethods()   B

Complexity

Conditions 8
Paths 2

Size

Total Lines 42

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 8
nc 2
nop 5
dl 0
loc 42
rs 8.0035
c 0
b 0
f 0
1
<?php
2
3
/**
4
 * File contains Test class.
5
 *
6
 * @copyright Copyright (C) eZ Systems AS. All rights reserved.
7
 * @license For full copyright and license information view LICENSE file distributed with this source code.
8
 */
9
declare(strict_types=1);
10
11
namespace eZ\Publish\Core\Persistence\Cache\Tests;
12
13
/**
14
 * Abstract test case for spi cache impl.
15
 */
16
abstract class AbstractCacheHandlerTest extends AbstractBaseHandlerTest
17
{
18
    abstract public function getHandlerMethodName(): string;
19
20
    abstract public function getHandlerClassName(): string;
21
22
    abstract public function providerForUnCachedMethods(): array;
23
24
    /**
25
     * @dataProvider providerForUnCachedMethods
26
     *
27
     * @param string $method
28
     * @param array $arguments
29
     * @param array|null $tags
30
     * @param string|array|null $key
31
     * @param mixed $returnValue
32
     */
33
    final public function testUnCachedMethods(string $method, array $arguments, array $tags = null, $key = null, $returnValue = null)
34
    {
35
        $handlerMethodName = $this->getHandlerMethodName();
36
37
        $this->loggerMock->expects($this->once())->method('logCall');
38
        $this->loggerMock->expects($this->never())->method('logCacheHit');
39
        $this->loggerMock->expects($this->never())->method('logCacheMiss');
40
41
        $innerHandler = $this->createMock($this->getHandlerClassName());
42
        $this->persistenceHandlerMock
43
            ->expects($this->once())
44
            ->method($handlerMethodName)
45
            ->will($this->returnValue($innerHandler));
46
47
        $innerHandler
48
            ->expects($this->once())
49
            ->method($method)
50
            ->with(...$arguments)
51
            ->will($this->returnValue($returnValue));
52
53
        if ($tags || $key) {
54
            $this->cacheMock
55
                ->expects(!empty($tags) ? $this->once() : $this->never())
56
                ->method('invalidateTags')
57
                ->with($tags);
58
59
            $this->cacheMock
60
                ->expects(!empty($key) && is_string($key) ? $this->once() : $this->never())
61
                ->method('deleteItem')
62
                ->with($key);
63
64
            $this->cacheMock
65
                ->expects(!empty($key) && is_array($key) ? $this->once() : $this->never())
66
                ->method('deleteItems')
67
                ->with($key);
68
        }
69
70
        $handler = $this->persistenceCacheHandler->$handlerMethodName();
71
        $actualReturnValue = call_user_func_array([$handler, $method], $arguments);
72
73
        $this->assertEquals($returnValue, $actualReturnValue);
74
    }
75
76
    abstract public function providerForCachedLoadMethods(): array;
77
78
    /**
79
     * @dataProvider providerForCachedLoadMethods
80
     *
81
     * @param string $method
82
     * @param array $arguments
83
     * @param string $key
84
     * @param mixed $data
85
     * @param bool $multi Default false, set to true if method will lookup several cache items.
86
     * @param array $additionalCalls Sets of additional calls being made to handlers, with 4 values (0: handler name, 1: handler class, 2: method, 3: return data)
87
     */
88
    final public function testLoadMethodsCacheHit(string $method, array $arguments, string $key, $data = null, bool $multi = false, array $additionalCalls = [])
89
    {
90
        $cacheItem = $this->getCacheItem($key, $multi ? reset($data) : $data);
91
        $handlerMethodName = $this->getHandlerMethodName();
92
93
        $this->loggerMock->expects($this->never())->method('logCall');
94
95 View Code Duplication
        if ($multi) {
0 ignored issues
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...
96
            $this->cacheMock
97
                ->expects($this->once())
98
                ->method('getItems')
99
                ->with([$cacheItem->getKey()])
100
                ->willReturn([$key => $cacheItem]);
101
        } else {
102
            $this->cacheMock
103
                ->expects($this->once())
104
                ->method('getItem')
105
                ->with($cacheItem->getKey())
106
                ->willReturn($cacheItem);
107
        }
108
109
        $this->persistenceHandlerMock
110
            ->expects($this->never())
111
            ->method($handlerMethodName);
112
113
        foreach ($additionalCalls as $additionalCall) {
114
            $this->persistenceHandlerMock
115
                ->expects($this->never())
116
                ->method($additionalCall[0]);
117
        }
118
119
        $handler = $this->persistenceCacheHandler->$handlerMethodName();
120
        $return = call_user_func_array([$handler, $method], $arguments);
121
122
        $this->assertEquals($data, $return);
123
    }
124
125
    /**
126
     * @dataProvider providerForCachedLoadMethods
127
     *
128
     * @param string $method
129
     * @param array $arguments
130
     * @param string $key
131
     * @param object $data
132
     * @param bool $multi Default false, set to true if method will lookup several cache items.
133
     * @param array $additionalCalls Sets of additional calls being made to handlers, with 4 values (0: handler name, 1: handler class, 2: method, 3: return data)
134
     */
135
    final public function testLoadMethodsCacheMiss(string $method, array $arguments, string $key, $data = null, bool $multi = false, array $additionalCalls = [])
136
    {
137
        $cacheItem = $this->getCacheItem($key, null);
138
        $handlerMethodName = $this->getHandlerMethodName();
139
140
        $this->loggerMock->expects($this->once())->method('logCall');
141
142 View Code Duplication
        if ($multi) {
0 ignored issues
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...
143
            $this->cacheMock
144
                ->expects($this->once())
145
                ->method('getItems')
146
                ->with([$cacheItem->getKey()])
147
                ->willReturn([$key => $cacheItem]);
148
        } else {
149
            $this->cacheMock
150
                ->expects($this->once())
151
                ->method('getItem')
152
                ->with($cacheItem->getKey())
153
                ->willReturn($cacheItem);
154
        }
155
156
        $innerHandlerMock = $this->createMock($this->getHandlerClassName());
157
        $this->persistenceHandlerMock
158
            ->expects($this->once())
159
            ->method($handlerMethodName)
160
            ->willReturn($innerHandlerMock);
161
162
        $innerHandlerMock
163
            ->expects($this->once())
164
            ->method($method)
165
            ->with(...$arguments)
166
            ->willReturn($data);
167
168 View Code Duplication
        foreach ($additionalCalls as $additionalCall) {
0 ignored issues
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...
169
            $innerHandlerMock = $this->createMock($additionalCall[1]);
170
            $this->persistenceHandlerMock
171
                ->expects($this->once())
172
                ->method($additionalCall[0])
173
                ->willReturn($innerHandlerMock);
174
175
            $innerHandlerMock
176
                ->expects($this->once())
177
                ->method($additionalCall[2])
178
                ->willReturn($additionalCall[3]);
179
        }
180
181
        $this->cacheMock
182
            ->expects($this->once())
183
            ->method('save')
184
            ->with($cacheItem);
185
186
        $handler = $this->persistenceCacheHandler->$handlerMethodName();
187
        $return = call_user_func_array([$handler, $method], $arguments);
188
189
        $this->assertEquals($data, $return);
190
191
        // Assert use of tags would probably need custom logic as internal property is [$tag => $tag] value and we don't want to know that.
192
        //$this->assertAttributeEquals([], 'tags', $cacheItem);
193
    }
194
}
195