Completed
Push — master ( c77195...330b60 )
by Axel
10:09 queued 04:41
created

ParameterBag::prepareTitle()   B

Complexity

Conditions 9
Paths 9

Size

Total Lines 30
Code Lines 19

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 9
eloc 19
nc 9
nop 1
dl 0
loc 30
rs 8.0555
c 0
b 0
f 0
1
<?php
2
3
declare(strict_types=1);
4
5
/*
6
 * This file is part of the Zikula package.
7
 *
8
 * Copyright Zikula Foundation - https://ziku.la/
9
 *
10
 * For the full copyright and license information, please view the LICENSE
11
 * file that was distributed with this source code.
12
 */
13
14
namespace Zikula\ThemeModule\Engine;
15
16
use Countable;
17
use IteratorAggregate;
18
19
/**
20
 * This class provides an abstracted method of collecting, managing and retrieving variables.
21
 * values can be stored in a namespaced array structure. i.e.
22
 *   'key' = ['subkey' => value, 'subkey2' => value2]
23
 *      or
24
 *   'key.subkey' = value
25
 *   'key.subkey2' = value2
26
 */
27
class ParameterBag implements IteratorAggregate, Countable
28
{
29
    /**
30
     * @var array
31
     */
32
    private $parameters;
33
34
    /**
35
     * Namespace character.
36
     *
37
     * @var string
38
     */
39
    private $ns;
40
41
    public function __construct(
42
        array $parameters = [],
43
        $namespaceChar = '.'
44
    ) {
45
        $this->parameters = $parameters;
46
        $this->ns = $namespaceChar;
47
    }
48
49
    /**
50
     * Allows Twig to fetch properties without use of ArrayAccess
51
     *
52
     * ArrayAccess is problematic because Twig uses isset() to
53
     * check if property field exists, so it's not possible
54
     * to get using default values, ie, empty.
55
     *
56
     * @param mixed $args
57
     * @return mixed
58
     */
59
    public function __call(string $key, $args)
60
    {
61
        return $this->get($key);
62
    }
63
64
    public function has(string $key): bool
65
    {
66
        $parameters = $this->resolvePath($key);
67
        $key = $this->resolveKey($key);
68
69
        return array_key_exists($key, $parameters);
70
    }
71
72
    /**
73
     * Gets key.
74
     *
75
     * @param mixed $default
76
     * @return mixed
77
     */
78
    public function get(string $key, $default = '')
79
    {
80
        $parameters = $this->resolvePath($key);
81
        $key = $this->resolveKey($key);
82
83
        return array_key_exists($key, $parameters) ? $parameters[$key] : $default;
84
    }
85
86
    /**
87
     * Sets value.
88
     *   can use 'key' = ['subkey' => value, 'subkey2' => value2]
89
     *      or
90
     *   'key.subkey' = value
91
     *   'key.subkey2' = value2
92
     *
93
     * @param mixed $value
94
     */
95
    public function set(string $key, $value)
96
    {
97
        $parameters = &$this->resolvePath($key, true);
98
        $key = $this->resolveKey($key);
99
        $parameters[$key] = $value;
100
    }
101
102
    /**
103
     * Removes and returns value.
104
     *
105
     * @return mixed
106
     */
107
    public function remove(string $key)
108
    {
109
        $retval = null;
110
        $parameters = &$this->resolvePath($key);
111
        $key = $this->resolveKey($key);
112
        if (array_key_exists($key, $parameters)) {
113
            $retval = $parameters[$key];
114
            unset($parameters[$key]);
115
        }
116
117
        return $retval;
118
    }
119
120
    /**
121
     * Retrieve all parameters.
122
     */
123
    public function all(): array
124
    {
125
        return $this->parameters;
126
    }
127
128
    /**
129
     * Switch out array.
130
     */
131
    public function replace(array $parameters = []): void
132
    {
133
        $this->parameters = [];
134
        foreach ($parameters as $key => $value) {
135
            $this->set($key, $value);
136
        }
137
    }
138
139
    /**
140
     * Clears and return all parameters.
141
     */
142
    public function clear(): array
143
    {
144
        $return = $this->parameters;
145
        $this->parameters = [];
146
147
        return $return;
148
    }
149
150
    /**
151
     * Returns an iterator for parameters.
152
     */
153
    public function getIterator(): ArrayIterator
0 ignored issues
show
Bug introduced by
The type Zikula\ThemeModule\Engine\ArrayIterator was not found. Did you mean ArrayIterator? If so, make sure to prefix the type with \.
Loading history...
154
    {
155
        return new ArrayIterator($this->parameters);
156
    }
157
158
    /**
159
     * Returns the number of parameters.
160
     */
161
    public function count(): int
162
    {
163
        return count($this->parameters);
164
    }
165
166
    /**
167
     * Resolves a path in parameters property and returns it as a reference.
168
     *
169
     * This method allows structured namespacing of parameters.
170
     */
171
    private function &resolvePath(string $key, bool $writeContext = false): array
172
    {
173
        $array = &$this->parameters;
174
        $key = (0 === mb_strpos($key, $this->ns)) ? mb_substr($key, 1) : $key;
175
176
        // Check if there is anything to do, else return
177
        if (!$key) {
178
            return $array;
179
        }
180
181
        $parts = explode($this->ns, $key);
182
        if (count($parts) < 2) {
183
            if (!$writeContext) {
184
                return $array;
185
            }
186
187
            $array[$parts[0]] = [];
188
189
            return $array;
190
        }
191
192
        unset($parts[count($parts) - 1]);
193
194
        foreach ($parts as $part) {
195
            if (!array_key_exists($part, $array)) {
196
                if (!$writeContext) {
197
                    return $array;
198
                }
199
200
                $array[$part] = [];
201
            }
202
203
            $array = &$array[$part];
204
        }
205
206
        return $array;
207
    }
208
209
    /**
210
     * Resolves the key from the name.
211
     * This is the last part in a dot separated string.
212
     */
213
    private function resolveKey(string $key): string
214
    {
215
        if (false !== mb_strpos($key, $this->ns)) {
216
            $key = mb_substr($key, mb_strrpos($key, $this->ns) + 1, mb_strlen($key));
217
        }
218
219
        return $key;
220
    }
221
}
222