Completed
Push — master ( 8737d4...f858fc )
by Pol
15:13
created

DynamicObjectsTrait::__get()   A

Complexity

Conditions 3
Paths 3

Size

Total Lines 15
Code Lines 8

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 8
CRAP Score 3

Importance

Changes 0
Metric Value
dl 0
loc 15
ccs 8
cts 8
cp 1
rs 9.4285
c 0
b 0
f 0
cc 3
eloc 8
nc 3
nop 1
crap 3
1
<?php
2
3
namespace drupol\DynamicObjects;
4
5
use drupol\Memoize\MemoizeTrait;
6
use Psr\SimpleCache\CacheInterface;
7
use Symfony\Component\Cache\Simple\ArrayCache;
8
9
/**
10
 * Trait DynamicObjectsTrait.
11
 *
12
 * @package drupol\DynamicObjects
13
 */
14
trait DynamicObjectsTrait
15
{
16
    use MemoizeTrait;
17
18
    /**
19
     * @var array
20
     */
21
    protected static $dynamicMethods = array();
22
23
    /**
24
     * @var array
25
     */
26
    protected static $dynamicProperties = array();
27
28
    /**
29
     * Add a dynamic property.
30
     *
31
     * @param string $name
32
     *   The property name.
33
     * @param mixed $value
34
     *   The property value.
35
     * @param bool $memoize
36
     *   Memoize parameter.
37
     */
38
    public static function addDynamicProperty($name, $value, $memoize = false)
39
    {
40 5
        static::$dynamicProperties[get_called_class()][$name] = [
41
          'name' => $name,
42 5
          'factory' => $value,
43 5
          'memoize' => $memoize,
44 5
        ];
45 5
    }
46
47 5
    /**
48
     * Add a dynamic method.
49
     *
50
     * @param $name
51
     *   The method name.
52
     * @param \Closure $func
53
     *   The method.
54
     * @param bool $memoize
55
     *   Memoize parameter.
56
     */
57
    public static function addDynamicMethod($name, \Closure $func, $memoize = false)
58
    {
59 4
        static::$dynamicMethods[get_called_class()][$name] = [
60
          'name' => $name,
61 4
          'factory' => $func,
62 4
          'memoize' => $memoize,
63 4
        ];
64 4
    }
65
66 4
    /**
67
     * Check if a dynamic property exists.
68
     *
69
     * @param string $name
70
     *   The property name.
71
     * @return bool
72
     *   True if the property exists, false otherwise.
73
     */
74
    public static function hasDynamicProperty($name)
75
    {
76 8
        return isset(static::$dynamicProperties[get_called_class()][$name]);
77
    }
78 8
79
    /**
80
     * Check if a dynamic method exists.
81
     *
82
     * @param string $name
83
     *   The property name.
84
     * @return bool
85
     *   True if the property exists, false otherwise.
86
     */
87
    public static function hasDynamicMethod($name)
88
    {
89 6
        return isset(static::$dynamicMethods[get_called_class()][$name]);
90
    }
91 6
92
    /**
93
     * Get a dynamic property.
94
     *
95
     * @param $name
96
     *   The property name.
97
     * @return mixed|null
98
     *   The property value if it exists, null otherwise.
99
     */
100
    public static function getDynamicProperty($name)
101
    {
102 4
        if (static::hasDynamicProperty($name)) {
103
            return static::$dynamicProperties[get_called_class()][$name];
104 4
        }
105 3
106
        return null;
107
    }
108 1
109
    /**
110
     * Get a dynamic method.
111
     *
112
     * @param $name
113
     *   The method name.
114
     * @return mixed|null
115
     *   The method if it exists, null otherwise.
116
     */
117
    public static function getDynamicMethod($name)
118
    {
119 2
        return ( static::hasDynamicMethod($name) ) ?
120
          static::$dynamicMethods[get_called_class()][$name] : null;
121 2
    }
122 2
123
    /**
124
     * Clear dynamic properties.
125
     */
126
    public static function clearDynamicProperties()
127
    {
128 1
        static::$dynamicProperties[get_called_class()] = array();
129
    }
130 1
131 1
    /**
132
     * Clear dynamic methods.
133
     */
134
    public static function clearDynamicMethods()
135
    {
136 1
        static::$dynamicMethods[get_called_class()] = array();
137
    }
138 1
139 1
    /**
140
     * Remove a dynamic property.
141
     *
142
     * @param string $name
143
     *   The property name.
144
     */
145
    public static function removeDynamicProperty($name)
146
    {
147 1
        unset(static::$dynamicProperties[get_called_class()][$name]);
148
    }
149 1
150 1
    /**
151
     * Remove a dynamic method.
152
     *
153
     * @param string $name
154
     *   The method name.
155
     */
156
    public static function removeDynamicMethod($name)
157
    {
158 1
        unset(static::$dynamicMethods[get_called_class()][$name]);
159
    }
160 1
161 1
    /**
162
     * Execute a closure.
163
     *
164
     * @param \Closure $func
165
     *   The closure.
166
     * @param array $parameters
167
     *   The closure's parameters.
168 3
     * @param bool $memoize
169
     *   The memoize parameter.
170 3
     *
171 3
     * @return mixed|null
172
     *   The return of the closure.
173
     *
174
     * @throws \Psr\SimpleCache\InvalidArgumentException
175
     */
176
    public function doDynamicRequest(\Closure $func, array $parameters = [], $memoize = false)
177
    {
178 6
        if (!class_exists('\drupol\Memoize\Memoize')) {
179
            $memoize = false;
180 6
        }
181 1
182
        if (true === $memoize) {
183
            return $this->memoize($func, $parameters);
184 6
        }
185
186
        return call_user_func_array($func, $parameters);
187
    }
188
189
    /**
190 1
     * @param $method
191
     * @param array $parameters
192 1
     *
193 1
     * @return mixed
194
     * @throws \Psr\SimpleCache\InvalidArgumentException
195
     */
196
    public function __call($method, array $parameters = array())
197
    {
198
        if (static::hasDynamicMethod($method)) {
199
            $data = static::getDynamicMethod($method);
200
            return $this->doDynamicRequest($data['factory'], $parameters, $data['memoize']);
201
        }
202
203
        throw new \BadMethodCallException(sprintf('Undefined method: %s().', $method));
204
    }
205
206
    /**
207
     * {inheritdoc}
208
     */
209
    public function __get($property)
210 4
    {
211
        if (static::hasDynamicProperty($property)) {
212 4
            $data = static::getDynamicProperty($property);
213
214 4
            $return = $data['factory'];
215 2
            if (is_callable($data['factory'])) {
216 2
                $return = $this->doDynamicRequest($data['factory'], [], $data['memoize']);
217
            }
218
219
            return $return;
220 4
        }
221
222 4
        throw new \DomainException(sprintf('Undefined property: %s().', $property));
223 2
    }
224
225
    /**
226 4
     * {inheritdoc}
227
     */
228
    public function __set($property, $value)
229
    {
230
        if (static::hasDynamicProperty($property)) {
231
            static::addDynamicProperty($property, $value);
232
        }
233
    }
234
}
235