Completed
Push — spi_log_cache_hits ( 9f001e )
by André
21:42
created

PersistenceLogger   A

Complexity

Total Complexity 20

Size/Duplication

Total Lines 164
Duplicated Lines 15.85 %

Coupling/Cohesion

Components 2
Dependencies 0

Importance

Changes 0
Metric Value
dl 26
loc 164
rs 10
c 0
b 0
f 0
wmc 20
lcom 2
cbo 0

13 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 4 1
A logCall() 13 13 2
A logCacheHit() 13 13 2
A getCacheCallData() 0 8 1
A getSimpleCallTrace() 0 19 5
A logUnCachedHandler() 0 7 2
A getName() 0 4 1
A getCount() 0 4 1
A isCallsLoggingEnabled() 0 4 1
A getCalls() 0 4 1
A getCacheMisses() 0 4 1
A getCacheHits() 0 4 1
A getLoadedUnCachedHandlers() 0 4 1

How to fix   Duplicated Code   

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:

1
<?php
2
3
/**
4
 * File containing the Persistence Cache SPI logger 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
namespace eZ\Publish\Core\Persistence\Cache;
10
11
/**
12
 * Log un-cached use of SPI Persistence.
13
 *
14
 * Stops logging details when reaching $maxLogCalls to conserve memory use
15
 */
16
class PersistenceLogger
17
{
18
    const NAME = 'PersistenceLogger';
19
20
    /** @var bool */
21
    protected $logCalls = true;
22
23
    /** @var array */
24
    protected $misses = [];
25
26
    /** @var array */
27
    protected $hits = [];
28
29
    /** @var array */
30
    protected $unCachedHandlers = array();
31
32
    /**
33
     * @param bool $logCalls Flag to enable logging of calls or not, should be disabled in prod
34
     */
35
    public function __construct($logCalls = true)
36
    {
37
        $this->logCalls = $logCalls;
38
    }
39
40
    /**
41
     * Log cache misses and SPI calls with method name and arguments.
42
     *
43
     * @param string $method
44
     * @param array $arguments
45
     */
46 View Code Duplication
    public function logCall($method, array $arguments = [])
47
    {
48
        if ($this->logCalls) {
49
            $this->misses[] = $this->getCacheCallData(
50
                $method,
51
                $arguments,
52
                array_slice(
53
                    debug_backtrace(DEBUG_BACKTRACE_IGNORE_ARGS, 7),
54
                    2
55
                )
56
            );
57
        }
58
    }
59
60
    /**
61
     * Log a Cache hit, which means further SPI calls are not needed.
62
     *
63
     * @param string $method
64
     * @param array $arguments
65
     */
66 View Code Duplication
    public function logCacheHit($method, array $arguments = [])
67
    {
68
        if ($this->logCalls) {
69
            $this->hits[] = $this->getCacheCallData(
70
                $method,
71
                $arguments,
72
                array_slice(
73
                    debug_backtrace(DEBUG_BACKTRACE_IGNORE_ARGS, 7),
74
                    2
75
                )
76
            );
77
        }
78
    }
79
80
    private function getCacheCallData($method, array $arguments, array $trimmedBacktrace)
81
    {
82
        return [
83
            'method' => $method,
84
            'arguments' => $arguments,
85
            'trace' => $this->getSimpleCallTrace($trimmedBacktrace),
86
        ];
87
    }
88
89
    private function getSimpleCallTrace(array $backtrace): array
90
    {
91
        $calls = [];
92
        foreach ($backtrace as $call) {
93
            if (!isset($call['class']) || strpos($call['class'], '\\') === false) {
94
                // skip if class has no namspace (Symfony lazy proxy) or plain function
95
                continue;
96
            }
97
98
            $calls[] = $call['class'] . $call['type'] . $call['function'] . '()';
99
100
            // Break out as soon as we have listed 1 class outside of kernel
101
            if (strpos($call['class'], 'eZ\\Publish\\Core\\') !== 0) {
102
                break;
103
            }
104
        }
105
106
        return $calls;
107
    }
108
109
    /**
110
     * Log uncached handler being loaded.
111
     *
112
     * @param string $handler
113
     */
114
    public function logUnCachedHandler($handler)
115
    {
116
        if (!isset($this->unCachedHandlers[$handler])) {
117
            $this->unCachedHandlers[$handler] = 0;
118
        }
119
        ++$this->unCachedHandlers[$handler];
120
    }
121
122
    /**
123
     * @return string
124
     */
125
    public function getName()
126
    {
127
        return self::NAME;
128
    }
129
130
    /**
131
     * @deprecated since 7.3, count the hits or misses instead.
132
     * @return int
133
     */
134
    public function getCount()
135
    {
136
        return count($this->misses);
137
    }
138
139
    /**
140
     * @return bool
141
     */
142
    public function isCallsLoggingEnabled()
143
    {
144
        return $this->logCalls;
145
    }
146
147
    /**
148
     * @deprecated Since 7.3, use getCacheMisses()
149
     * @return array
150
     */
151
    public function getCalls()
152
    {
153
        return $this->misses;
154
    }
155
156
    /**
157
     * @return array
158
     */
159
    public function getCacheMisses()
160
    {
161
        return $this->misses;
162
    }
163
164
    /**
165
     * @return array
166
     */
167
    public function getCacheHits()
168
    {
169
        return $this->hits;
170
    }
171
172
    /**
173
     * @return array
174
     */
175
    public function getLoadedUnCachedHandlers()
176
    {
177
        return $this->unCachedHandlers;
178
    }
179
}
180