This project does not seem to handle request data directly as such no vulnerable execution paths were found.
include
, or for example
via PHP's auto-loading mechanism.
These results are based on our legacy PHP analysis, consider migrating to our new PHP analysis engine instead. Learn more
1 | <?php |
||
2 | |||
3 | namespace Yokai\MessengerBundle\DependencyInjection; |
||
4 | |||
5 | use Symfony\Component\Config\Definition\Builder\ArrayNodeDefinition; |
||
6 | use Symfony\Component\Config\Definition\Builder\NodeDefinition; |
||
7 | use Symfony\Component\Config\Definition\Builder\TreeBuilder; |
||
8 | use Symfony\Component\Config\Definition\ConfigurationInterface; |
||
9 | |||
10 | /** |
||
11 | * @author Yann Eugoné <[email protected]> |
||
12 | */ |
||
13 | class Configuration implements ConfigurationInterface |
||
14 | { |
||
15 | /** |
||
16 | * @inheritdoc |
||
17 | */ |
||
18 | 14 | public function getConfigTreeBuilder() |
|
19 | { |
||
20 | 14 | $builder = $this->getBuilder(); |
|
21 | 14 | $root = $builder->root('yokai_messenger'); |
|
22 | |||
23 | $root |
||
24 | 14 | ->addDefaultsIfNotSet() |
|
25 | 14 | ->fixXmlConfig('message') |
|
26 | 14 | ->children() |
|
27 | 14 | ->scalarNode('logging_channel')->defaultValue('app')->end() |
|
28 | 14 | ->append($this->getContentBuilderNode()) |
|
29 | 14 | ->append($this->getChannelsNode()) |
|
30 | 14 | ->append($this->getMessagesNode()) |
|
31 | 14 | ->end() |
|
32 | ; |
||
33 | |||
34 | 14 | return $builder; |
|
35 | } |
||
36 | |||
37 | /** |
||
38 | * @return TreeBuilder |
||
39 | */ |
||
40 | 14 | private function getBuilder() |
|
41 | { |
||
42 | 14 | return new TreeBuilder(); |
|
43 | } |
||
44 | |||
45 | /** |
||
46 | * @param string $name |
||
47 | * |
||
48 | * @return ArrayNodeDefinition |
||
49 | */ |
||
50 | 14 | private function root($name) |
|
51 | { |
||
52 | 14 | return $this->getBuilder()->root($name); |
|
53 | } |
||
54 | |||
55 | /** |
||
56 | * @return NodeDefinition |
||
57 | */ |
||
58 | 14 | private function getChannelsNode() |
|
59 | { |
||
60 | 14 | $node = $this->root('channels'); |
|
61 | |||
62 | $node |
||
63 | 14 | ->addDefaultsIfNotSet() |
|
64 | 14 | ->children() |
|
65 | 14 | ->append($this->getSwiftmailerChannelNode()) |
|
66 | 14 | ->append($this->getTwilioChannelNode()) |
|
67 | 14 | ->append($this->getDoctrineChannelNode()) |
|
68 | 14 | ->append($this->getMobileChannelNode()) |
|
69 | 14 | ->end() |
|
70 | ; |
||
71 | |||
72 | 14 | return $node; |
|
73 | } |
||
74 | |||
75 | /** |
||
76 | * @return NodeDefinition |
||
77 | */ |
||
78 | 14 | private function getMessagesNode() |
|
79 | { |
||
80 | 14 | $node = $this->root('messages'); |
|
81 | |||
82 | $node |
||
0 ignored issues
–
show
|
|||
83 | 14 | ->defaultValue([]) |
|
84 | 14 | ->prototype('array') |
|
85 | 14 | ->fixXmlConfig('channel') |
|
86 | 14 | ->children() |
|
87 | 14 | ->scalarNode('id')->isRequired()->end() |
|
88 | 14 | ->arrayNode('channels') |
|
89 | 14 | ->beforeNormalization() |
|
90 | 14 | ->ifString()->then($this->stringToArray()) |
|
91 | 14 | ->end() |
|
92 | 14 | ->requiresAtLeastOneElement() |
|
93 | 14 | ->prototype('scalar')->end() |
|
94 | 14 | ->end() |
|
95 | 14 | ->arrayNode('defaults') |
|
96 | 14 | ->defaultValue([]) |
|
97 | 14 | ->prototype('variable')->end() |
|
98 | 14 | ->end() |
|
99 | 14 | ->arrayNode('options') |
|
100 | 14 | ->defaultValue([]) |
|
101 | 14 | ->useAttributeAsKey('channel') |
|
102 | 14 | ->prototype('variable') |
|
103 | 14 | ->validate() |
|
104 | 14 | ->ifTrue($this->isNotHash()) |
|
105 | 14 | ->thenInvalid('Expected a hash for channel options, got %s.') |
|
106 | 14 | ->end() |
|
107 | 14 | ->end() |
|
108 | 14 | ->end() |
|
109 | 14 | ->end() |
|
110 | 14 | ->end() |
|
111 | ; |
||
112 | |||
113 | 14 | return $node; |
|
114 | } |
||
115 | |||
116 | /** |
||
117 | * @return NodeDefinition |
||
118 | */ |
||
119 | 14 | private function getSwiftmailerChannelNode() |
|
120 | { |
||
121 | 14 | $node = $this->root('swiftmailer'); |
|
122 | |||
123 | $node |
||
0 ignored issues
–
show
It seems like you code against a specific sub-type and not the parent class
Symfony\Component\Config...\Builder\NodeDefinition as the method children() does only exist in the following sub-classes of Symfony\Component\Config...\Builder\NodeDefinition : Symfony\Component\Config...der\ArrayNodeDefinition . Maybe you want to instanceof check for one of these explicitly?
Let’s take a look at an example: abstract class User
{
/** @return string */
abstract public function getPassword();
}
class MyUser extends User
{
public function getPassword()
{
// return something
}
public function getDisplayName()
{
// return some name.
}
}
class AuthSystem
{
public function authenticate(User $user)
{
$this->logger->info(sprintf('Authenticating %s.', $user->getDisplayName()));
// do something.
}
}
In the above example, the authenticate() method works fine as long as you just pass instances of MyUser. However, if you now also want to pass a different sub-classes of User which does not have a getDisplayName() method, the code will break. Available Fixes
Note: PHP Analyzer uses reverse abstract interpretation to narrow down the types
inside the if block in such a case.
![]() |
|||
124 | 14 | ->canBeEnabled() |
|
125 | 14 | ->validate() |
|
126 | 14 | ->ifTrue($this->nodeRequiredIfEnabled('from')) |
|
127 | 14 | ->thenInvalid($this->nodeMustBeConfigured('from', 'channels.swiftmailer')) |
|
128 | 14 | ->end() |
|
129 | 14 | ->children() |
|
130 | 14 | ->arrayNode('from') |
|
131 | 14 | ->normalizeKeys(false) |
|
132 | 14 | ->beforeNormalization() |
|
133 | 14 | ->ifString()->then($this->stringToArray()) |
|
134 | 14 | ->end() |
|
135 | 14 | ->requiresAtLeastOneElement() |
|
136 | 14 | ->prototype('scalar')->end() |
|
137 | 14 | ->end() |
|
138 | 14 | ->scalarNode('translator_catalog')->defaultValue('notifications')->end() |
|
139 | 14 | ->end() |
|
140 | ; |
||
141 | |||
142 | 14 | return $node; |
|
143 | } |
||
144 | |||
145 | /** |
||
146 | * @return NodeDefinition |
||
147 | */ |
||
148 | 14 | private function getTwilioChannelNode() |
|
149 | { |
||
150 | 14 | $node = $this->root('twilio'); |
|
151 | |||
152 | $node |
||
0 ignored issues
–
show
It seems like you code against a specific sub-type and not the parent class
Symfony\Component\Config...\Builder\NodeDefinition as the method children() does only exist in the following sub-classes of Symfony\Component\Config...\Builder\NodeDefinition : Symfony\Component\Config...der\ArrayNodeDefinition . Maybe you want to instanceof check for one of these explicitly?
Let’s take a look at an example: abstract class User
{
/** @return string */
abstract public function getPassword();
}
class MyUser extends User
{
public function getPassword()
{
// return something
}
public function getDisplayName()
{
// return some name.
}
}
class AuthSystem
{
public function authenticate(User $user)
{
$this->logger->info(sprintf('Authenticating %s.', $user->getDisplayName()));
// do something.
}
}
In the above example, the authenticate() method works fine as long as you just pass instances of MyUser. However, if you now also want to pass a different sub-classes of User which does not have a getDisplayName() method, the code will break. Available Fixes
Note: PHP Analyzer uses reverse abstract interpretation to narrow down the types
inside the if block in such a case.
![]() |
|||
153 | 14 | ->canBeEnabled() |
|
154 | 14 | ->validate() |
|
155 | 14 | ->ifTrue($this->nodeRequiredIfEnabled('from')) |
|
156 | 14 | ->thenInvalid($this->nodeMustBeConfigured('from', 'channels.twilio')) |
|
157 | 14 | ->ifTrue($this->nodeRequiredIfEnabled('api_id')) |
|
158 | 14 | ->thenInvalid($this->nodeMustBeConfigured('api_id', 'channels.twilio')) |
|
159 | 14 | ->ifTrue($this->nodeRequiredIfEnabled('api_token')) |
|
160 | 14 | ->thenInvalid($this->nodeMustBeConfigured('api_token', 'channels.twilio')) |
|
161 | 14 | ->end() |
|
162 | 14 | ->children() |
|
163 | 14 | ->scalarNode('from')->end() |
|
164 | 14 | ->scalarNode('api_id')->end() |
|
165 | 14 | ->scalarNode('api_token')->end() |
|
166 | 14 | ->end() |
|
167 | ; |
||
168 | |||
169 | 14 | return $node; |
|
170 | } |
||
171 | |||
172 | /** |
||
173 | * @return NodeDefinition |
||
174 | */ |
||
175 | 14 | private function getDoctrineChannelNode() |
|
176 | { |
||
177 | 14 | $node = $this->root('doctrine'); |
|
178 | |||
179 | $node |
||
180 | 14 | ->canBeEnabled() |
|
181 | 14 | ->children() |
|
182 | 14 | ->scalarNode('manager')->defaultValue('default')->end() |
|
183 | 14 | ->end() |
|
184 | ; |
||
185 | |||
186 | 14 | return $node; |
|
187 | } |
||
188 | |||
189 | /** |
||
190 | * @return NodeDefinition |
||
191 | */ |
||
192 | 14 | private function getMobileChannelNode() |
|
193 | { |
||
194 | 14 | $node = $this->root('mobile'); |
|
195 | |||
196 | $node |
||
197 | 14 | ->canBeEnabled() |
|
198 | 14 | ->children() |
|
199 | 14 | ->scalarNode('environment')->defaultValue('dev')->end() |
|
200 | 14 | ->arrayNode('apns') |
|
201 | 14 | ->canBeDisabled() |
|
202 | 14 | ->validate() |
|
203 | 14 | ->ifTrue($this->nodeRequiredIfEnabled('certificate')) |
|
204 | 14 | ->thenInvalid($this->nodeMustBeConfigured('certificate', 'channels.mobile.apns')) |
|
205 | 14 | ->ifTrue($this->nodeRequiredIfEnabled('certificate')) |
|
206 | 14 | ->thenInvalid($this->nodeMustBeConfigured('pass_phrase', 'channels.mobile.apns')) |
|
207 | 14 | ->end() |
|
208 | 14 | ->children() |
|
209 | 14 | ->scalarNode('certificate')->defaultNull()->end() |
|
210 | 14 | ->scalarNode('pass_phrase')->defaultNull()->end() |
|
211 | 14 | ->end() |
|
212 | 14 | ->end() |
|
213 | 14 | ->arrayNode('gcm') |
|
214 | 14 | ->canBeDisabled() |
|
215 | 14 | ->validate() |
|
216 | 14 | ->ifTrue($this->nodeRequiredIfEnabled('api_key')) |
|
217 | 14 | ->thenInvalid($this->nodeMustBeConfigured('api_key', 'channels.mobile.gcm')) |
|
218 | 14 | ->end() |
|
219 | 14 | ->children() |
|
220 | 14 | ->scalarNode('api_key')->defaultNull()->end() |
|
221 | 14 | ->end() |
|
222 | 14 | ->end() |
|
223 | 14 | ->end() |
|
224 | ; |
||
225 | |||
226 | 14 | return $node; |
|
227 | } |
||
228 | |||
229 | /** |
||
230 | * @return NodeDefinition |
||
231 | */ |
||
232 | 14 | private function getContentBuilderNode() |
|
233 | { |
||
234 | 14 | $node = $this->root('content_builder'); |
|
235 | |||
236 | $node |
||
0 ignored issues
–
show
The call to the method
Symfony\Component\Config...r\NodeDefinition::end() seems un-needed as the method has no side-effects.
PHP Analyzer performs a side-effects analysis of your code. A side-effect is basically anything that might be visible after the scope of the method is left. Let’s take a look at an example: class User
{
private $email;
public function getEmail()
{
return $this->email;
}
public function setEmail($email)
{
$this->email = $email;
}
}
If we look at the $user = new User();
$user->getEmail(); // This line could safely be removed as it has no effect.
On the hand, if we look at the $user = new User();
$user->setEmail('email@domain'); // This line has a side-effect (it changes an
// instance variable).
![]() |
|||
237 | 14 | ->defaultValue([]) |
|
238 | 14 | ->useAttributeAsKey('name') |
|
239 | 14 | ->prototype('variable') |
|
240 | 14 | ->end() |
|
241 | ; |
||
242 | |||
243 | 14 | return $node; |
|
244 | } |
||
245 | |||
246 | /** |
||
247 | * @return callable |
||
248 | */ |
||
249 | private function stringToArray() |
||
250 | { |
||
251 | 14 | return function ($value) { |
|
252 | 2 | return [$value]; |
|
253 | 14 | }; |
|
254 | } |
||
255 | |||
256 | /** |
||
257 | * @return callable |
||
258 | */ |
||
259 | private function isNotHash() |
||
260 | { |
||
261 | 14 | return function ($value) { |
|
262 | if (!is_array($value)) { |
||
263 | return true; |
||
264 | } |
||
265 | |||
266 | if (array_values($value) === $value) { |
||
267 | return true; |
||
268 | } |
||
269 | |||
270 | return false; |
||
271 | 14 | }; |
|
272 | } |
||
273 | |||
274 | /** |
||
275 | * @param string $node |
||
276 | * |
||
277 | * @return callable |
||
278 | */ |
||
279 | private function nodeRequiredIfEnabled($node) |
||
280 | { |
||
281 | 14 | return function ($value) use ($node) { |
|
282 | 7 | if (!$value['enabled']) { |
|
283 | 1 | return false; |
|
284 | } |
||
285 | |||
286 | 6 | if (isset($value[$node]) && !empty($value[$node])) { |
|
287 | 6 | return false; |
|
288 | } |
||
289 | |||
290 | return true; |
||
291 | 14 | }; |
|
292 | } |
||
293 | |||
294 | /** |
||
295 | * @param string $node |
||
296 | * @param string $path |
||
297 | * |
||
298 | * @return string |
||
299 | */ |
||
300 | 14 | private function nodeMustBeConfigured($node, $path) |
|
301 | { |
||
302 | 14 | return sprintf( |
|
303 | 14 | 'The child node "%s" at path "yokai_messenger.%s" must be configured.', |
|
304 | 14 | $node, |
|
305 | 14 | $path |
|
306 | ); |
||
307 | } |
||
308 | } |
||
309 |
Let’s take a look at an example:
In the above example, the authenticate() method works fine as long as you just pass instances of MyUser. However, if you now also want to pass a different sub-classes of User which does not have a getDisplayName() method, the code will break.
Available Fixes
Change the type-hint for the parameter:
Add an additional type-check:
Add the method to the parent class: