Code Coverage
 
Lines
Functions and Methods
Classes and Traits
Total
100.00% covered (success)
100.00%
39 / 39
100.00% covered (success)
100.00%
22 / 22
CRAP
100.00% covered (success)
100.00%
1 / 1
AbstractCallable
100.00% covered (success)
100.00%
39 / 39
100.00% covered (success)
100.00%
22 / 22
29
100.00% covered (success)
100.00%
1 / 1
 setCallable
100.00% covered (success)
100.00%
2 / 2
100.00% covered (success)
100.00%
1 / 1
1
 getCallable
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 getCallableType
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 setParameters
100.00% covered (success)
100.00%
2 / 2
100.00% covered (success)
100.00%
1 / 1
1
 addParameters
100.00% covered (success)
100.00%
5 / 5
100.00% covered (success)
100.00%
1 / 1
3
 addParameter
100.00% covered (success)
100.00%
2 / 2
100.00% covered (success)
100.00%
1 / 1
1
 addNamedParameter
100.00% covered (success)
100.00%
2 / 2
100.00% covered (success)
100.00%
1 / 1
1
 getParameters
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 getParameter
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
2
 hasParameters
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 hasParameter
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 removeParameter
100.00% covered (success)
100.00%
3 / 3
100.00% covered (success)
100.00%
1 / 1
2
 removeParameters
100.00% covered (success)
100.00%
2 / 2
100.00% covered (success)
100.00%
1 / 1
1
 setConstructorParams
100.00% covered (success)
100.00%
2 / 2
100.00% covered (success)
100.00%
1 / 1
1
 getConstructorParams
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 getConstructorParam
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
2
 hasConstructorParams
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 hasConstructorParam
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 removeConstructorParam
100.00% covered (success)
100.00%
3 / 3
100.00% covered (success)
100.00%
1 / 1
2
 removeConstructorParams
100.00% covered (success)
100.00%
2 / 2
100.00% covered (success)
100.00%
1 / 1
1
 isCallable
100.00% covered (success)
100.00%
3 / 3
100.00% covered (success)
100.00%
1 / 1
2
 wasCalled
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 prepare
n/a
0 / 0
n/a
0 / 0
0
 prepareParameters
n/a
0 / 0
n/a
0 / 0
0
 call
n/a
0 / 0
n/a
0 / 0
0
1<?php
2declare(strict_types=1);
3/**
4 * Pop PHP Framework (https://www.popphp.org/)
5 *
6 * @link       https://github.com/popphp/popphp-framework
7 * @author     Nick Sagona, III <nick@popphp.org>
8 * @copyright  Copyright (c) 2009-2026 Nick Sagona, III
9 * @license    https://www.popphp.org/license     New BSD License
10 */
11
12/**
13 * @namespace
14 */
15namespace Pop\Utils;
16
17/**
18 * Pop utils callable object class
19 *
20 * @category   Pop
21 * @package    Pop\Utils
22 * @author     Nick Sagona, III <nick@popphp.org>
23 * @copyright  Copyright (c) 2009-2026 Nick Sagona, III
24 * @license    https://www.popphp.org/license     New BSD License
25 * @version    3.0.0
26 */
27abstract class AbstractCallable implements CallableInterface
28{
29
30    /**
31     * Call type constants
32     */
33    const FUNCTION                = 'FUNCTION';                // Function
34    const FUNCTION_PARAMS         = 'FUNCTION_PARAMS';         // Function w/ parameters
35    const CLOSURE                 = 'CLOSURE';                 // Closure
36    const CLOSURE_PARAMS          = 'CLOSURE_PARAMS';          // Closure w/ parameters
37    const STATIC_CALL             = 'STATIC_CALL';             // 'Class::method'
38    const STATIC_CALL_PARAMS      = 'STATIC_CALL_PARAMS';      // 'Class::method' w/ parameters
39    const INSTANCE_CALL           = 'INSTANCE_CALL';           // 'Class->method'
40    const INSTANCE_CALL_PARAMS    = 'INSTANCE_CALL_PARAMS';    // 'Class->method' w/ parameters
41    const CONSTRUCTOR_CALL        = 'CONSTRUCTOR_CALL';        // 'Class'
42    const CONSTRUCTOR_CALL_PARAMS = 'CONSTRUCTOR_CALL_PARAMS'; // 'Class' w/ parameters
43    const IS_CALLABLE             = 'IS_CALLABLE';             // Is a basic callable entity
44    const IS_CALLABLE_PARAMS      = 'IS_CALLABLE_PARAMS';      // Is a basic callable entity w/ parameters
45    const NEW_OBJECT              = 'NEW_OBJECT';              // 'new Class'
46    const NEW_OBJECT_PARAMS       = 'NEW_OBJECT_PARAMS';       // 'new Class' w/ parameters
47    const OBJECT                  = 'OBJECT';                  // Already an instantiated object
48    const OBJECT_PARAMS           = 'OBJECT_PARAMS';           // Already an instantiated object w/ parameters
49
50    /**
51     * Callable
52     * @var mixed
53     */
54    protected mixed $callable = null;
55
56    /**
57     * Parameters
58     * @var array
59     */
60    protected array $parameters = [];
61
62    /**
63     * Callable type
64     * @var ?string
65     */
66    protected ?string $callableType = null;
67
68    /**
69     * Was called flag
70     * @var bool
71     */
72    protected bool $wasCalled = false;
73
74    /**
75     * Callable class
76     * @var ?string
77     */
78    protected ?string $class = null;
79
80    /**
81     * Callable method
82     * @var ?string
83     */
84    protected ?string $method = null;
85
86    /**
87     * Constructor parameters for instance calls
88     * @var array
89     */
90    protected array $constructorParams = [];
91
92    /**
93     * Set callable
94     *
95     * @param  mixed $callable
96     * @return AbstractCallable
97     */
98    public function setCallable(mixed $callable): AbstractCallable
99    {
100        $this->callable = $callable;
101        return $this;
102    }
103
104    /**
105     * Get callable
106     *
107     * @return mixed
108     */
109    public function getCallable(): mixed
110    {
111        return $this->callable;
112    }
113
114    /**
115     * Get callable type
116     *
117     * @return ?string
118     */
119    public function getCallableType(): ?string
120    {
121        return $this->callableType;
122    }
123
124    /**
125     * Set parameters
126     *
127     * @param  array $parameters
128     * @return AbstractCallable
129     */
130    public function setParameters(array $parameters): AbstractCallable
131    {
132        $this->parameters = $parameters;
133        return $this;
134    }
135
136    /**
137     * Add parameters
138     *
139     * @param  array $parameters
140     * @return AbstractCallable
141     */
142    public function addParameters(array $parameters): AbstractCallable
143    {
144        foreach ($parameters as $key => $value) {
145            if (is_numeric($key)) {
146                $this->addParameter($value);
147            } else {
148                $this->addNamedParameter($key, $value);
149            }
150        }
151        return $this;
152    }
153
154    /**
155     * Add a parameter
156     *
157     * @param  mixed $parameter
158     * @return AbstractCallable
159     */
160    public function addParameter(mixed $parameter): AbstractCallable
161    {
162        $this->parameters[] = $parameter;
163        return $this;
164    }
165
166    /**
167     * Add a parameter
168     *
169     * @param  string $name
170     * @param  mixed  $parameter
171     * @return AbstractCallable
172     */
173    public function addNamedParameter(string $name, mixed $parameter): AbstractCallable
174    {
175        $this->parameters[$name] = $parameter;
176        return $this;
177    }
178
179    /**
180     * Get parameters
181     *
182     * @return array
183     */
184    public function getParameters(): array
185    {
186        return $this->parameters;
187    }
188
189    /**
190     * Get a parameter
191     *
192     * @param  string $key
193     * @return mixed
194     */
195    public function getParameter(string $key): mixed
196    {
197        return (isset($this->parameters[$key])) ? $this->parameters[$key] : null;
198    }
199
200    /**
201     * Has parameters
202     *
203     * @return bool
204     */
205    public function hasParameters(): bool
206    {
207        return !empty($this->parameters);
208    }
209
210    /**
211     * Has a parameter
212     *
213     * @param  string $key
214     * @return bool
215     */
216    public function hasParameter(string $key): bool
217    {
218        return isset($this->parameters[$key]);
219    }
220
221    /**
222     * Remove a parameter
223     *
224     * @param  string $key
225     * @return AbstractCallable
226     */
227    public function removeParameter(string $key): AbstractCallable
228    {
229        if (isset($this->parameters[$key])) {
230            unset($this->parameters[$key]);
231        }
232        return $this;
233    }
234
235    /**
236     * Remove all parameters
237     *
238     * @return AbstractCallable
239     */
240    public function removeParameters(): AbstractCallable
241    {
242        $this->parameters = [];
243        return $this;
244    }
245
246    /**
247     * Set constructor parameters
248     *
249     * @param  array $constructorParams
250     * @return AbstractCallable
251     */
252    public function setConstructorParams(array $constructorParams): AbstractCallable
253    {
254        $this->constructorParams = $constructorParams;
255        return $this;
256    }
257
258    /**
259     * Get constructor parameters for instance call
260     *
261     * @return array
262     */
263    public function getConstructorParams(): array
264    {
265        return $this->constructorParams;
266    }
267
268    /**
269     * Get a constructor parameter for instance call
270     *
271     * @param  string $key
272     * @return mixed
273     */
274    public function getConstructorParam(string $key): mixed
275    {
276        return (isset($this->constructorParams[$key])) ? $this->constructorParams[$key] : null;
277    }
278
279    /**
280     * Has constructor parameters for instance call
281     *
282     * @return bool
283     */
284    public function hasConstructorParams(): bool
285    {
286        return !empty($this->constructorParams);
287    }
288
289    /**
290     * Has a constructor parameter for instance call
291     *
292     * @param  string $key
293     * @return bool
294     */
295    public function hasConstructorParam(string $key): bool
296    {
297        return isset($this->constructorParams[$key]);
298    }
299
300    /**
301     * Remove a constructor parameter for instance call
302     *
303     * @param  string $key
304     * @return AbstractCallable
305     */
306    public function removeConstructorParam(string $key): AbstractCallable
307    {
308        if (isset($this->constructorParams[$key])) {
309            unset($this->constructorParams[$key]);
310        }
311        return $this;
312    }
313
314    /**
315     * Remove all constructor parameters for instance call
316     *
317     * @return AbstractCallable
318     */
319    public function removeConstructorParams(): AbstractCallable
320    {
321        $this->constructorParams = [];
322        return $this;
323    }
324
325    /**
326     * Check if object is callable
327     *
328     * @return bool
329     */
330    public function isCallable(): bool
331    {
332        if ($this->callableType === null) {
333            $this->prepare();
334        }
335
336        return ($this->callableType !== null);
337    }
338
339    /**
340     * Check if object was called
341     *
342     * @return bool
343     */
344    public function wasCalled(): bool
345    {
346        return $this->wasCalled;
347    }
348
349    /**
350     * Prepare object for call
351     *
352     * @return AbstractCallable
353     */
354    abstract public function prepare(): AbstractCallable;
355
356    /**
357     * Prepare parameters
358     *
359     * @return AbstractCallable
360     */
361    abstract public function prepareParameters(): AbstractCallable;
362
363    /**
364     * Execute the call
365     *
366     * @param  mixed $parameters
367     * @return mixed
368     */
369    abstract public function call(mixed $parameters = null): mixed;
370
371}