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 Nip; |
||
4 | |||
5 | use Nip\Config\ConfigAwareTrait; |
||
6 | use Nip\Dispatcher\Dispatcher; |
||
7 | use Nip\Dispatcher\DispatcherAwareTrait; |
||
8 | use Nip\Http\Response\Response; |
||
9 | use Nip\Http\Response\ResponseAwareTrait; |
||
10 | use Nip\Utility\Traits\NameWorksTrait; |
||
11 | use Symfony\Component\HttpKernel\Exception\NotFoundHttpException; |
||
12 | |||
13 | /** |
||
14 | * Class Controller |
||
15 | * @package Nip |
||
16 | * |
||
17 | * @method \Nip_Helper_Url Url() |
||
18 | * @method \Nip_Helper_Arrays Arrays() |
||
19 | * @method \Nip_Helper_Async Async() |
||
20 | */ |
||
21 | class Controller |
||
22 | { |
||
23 | use NameWorksTrait; |
||
24 | use ConfigAwareTrait; |
||
25 | use DispatcherAwareTrait; |
||
26 | use ResponseAwareTrait; |
||
27 | |||
28 | protected $fullName = null; |
||
29 | |||
30 | protected $name = null; |
||
31 | |||
32 | protected $action = null; |
||
33 | |||
34 | /** |
||
35 | * @var Request |
||
36 | */ |
||
37 | protected $request; |
||
38 | |||
39 | /** |
||
40 | * @var Helpers\AbstractHelper[] |
||
41 | */ |
||
42 | protected $helpers = []; |
||
43 | |||
44 | /** |
||
45 | * Controller constructor. |
||
46 | */ |
||
47 | 2 | public function __construct() |
|
48 | { |
||
49 | 2 | $name = str_replace("Controller", "", get_class($this)); |
|
50 | 2 | $this->name = inflector()->unclassify($name); |
|
51 | 2 | } |
|
52 | |||
53 | /** |
||
54 | * @param $name |
||
55 | * @param $arguments |
||
56 | * @return bool|mixed |
||
57 | */ |
||
58 | 1 | View Code Duplication | public function __call($name, $arguments) |
0 ignored issues
–
show
|
|||
59 | { |
||
60 | 1 | if ($name === ucfirst($name)) { |
|
61 | 1 | return $this->getHelper($name); |
|
62 | } |
||
63 | |||
64 | return trigger_error("Call to undefined method [$name] in controller [{$this->getClassName()}]", E_USER_ERROR); |
||
65 | } |
||
66 | |||
67 | /** |
||
68 | * @param $name |
||
69 | * @return Helpers\AbstractHelper |
||
70 | */ |
||
71 | 2 | public function getHelper($name) |
|
72 | { |
||
73 | 2 | return HelperBroker::get($name); |
|
74 | } |
||
75 | |||
76 | /** |
||
77 | * @return string |
||
78 | */ |
||
79 | public function getClassName() |
||
80 | { |
||
81 | return str_replace("Controller", "", get_class($this)); |
||
82 | } |
||
83 | |||
84 | /** |
||
85 | * @param null|Request $request |
||
86 | * @return Response |
||
87 | */ |
||
88 | public function dispatch($request = null) |
||
89 | { |
||
90 | $request = $request ? $request : $this->getRequest(); |
||
91 | $this->populateFromRequest($request); |
||
92 | |||
93 | return $this->dispatchAction($request->getActionName()); |
||
0 ignored issues
–
show
$request->getActionName() is of type string , but the function expects a boolean .
It seems like the type of the argument is not accepted by the function/method which you are calling. In some cases, in particular if PHP’s automatic type-juggling kicks in this might be fine. In other cases, however this might be a bug. We suggest to add an explicit type cast like in the following example: function acceptsInteger($int) { }
$x = '123'; // string "123"
// Instead of
acceptsInteger($x);
// we recommend to use
acceptsInteger((integer) $x);
![]() |
|||
94 | } |
||
95 | |||
96 | /** |
||
97 | * Returns the request Object |
||
98 | * @return Request |
||
99 | */ |
||
100 | public function getRequest() |
||
101 | { |
||
102 | if (!$this->request instanceof Request) { |
||
103 | $this->request = new Request(); |
||
104 | } |
||
105 | |||
106 | return $this->request; |
||
107 | } |
||
108 | |||
109 | /** |
||
110 | * @param Request $request |
||
111 | * @return self |
||
112 | */ |
||
113 | public function setRequest(Request $request) |
||
0 ignored issues
–
show
You have injected the Request via parameter
$request . This is generally not recommended as there might be multiple instances during a request cycle (f.e. when using sub-requests). Instead, it is recommended to inject the RequestStack and retrieve the current request each time you need it via getCurrentRequest() .
![]() |
|||
114 | { |
||
115 | $this->request = $request; |
||
116 | |||
117 | return $this; |
||
118 | } |
||
119 | |||
120 | /** |
||
121 | * @param Request $request |
||
122 | */ |
||
123 | public function populateFromRequest(Request $request) |
||
124 | { |
||
125 | $this->name = $request->getControllerName(); |
||
126 | $this->action = $request->getActionName(); |
||
127 | } |
||
128 | |||
129 | /** |
||
130 | * @param bool $action |
||
131 | * @return Response |
||
132 | */ |
||
133 | public function dispatchAction($action = false) |
||
134 | { |
||
135 | $action = Dispatcher::formatActionName($action); |
||
136 | |||
137 | if ($action) { |
||
138 | if ($this->validAction($action)) { |
||
139 | $this->setAction($action); |
||
140 | |||
141 | $this->parseRequest(); |
||
0 ignored issues
–
show
The call to the method
Nip\Controller::parseRequest() 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).
![]() |
|||
142 | $this->beforeAction(); |
||
0 ignored issues
–
show
The call to the method
Nip\Controller::beforeAction() 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).
![]() |
|||
143 | $this->{$action}(); |
||
144 | $this->afterAction(); |
||
0 ignored issues
–
show
The call to the method
Nip\Controller::afterAction() 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).
![]() |
|||
145 | |||
146 | return $this->getResponse(); |
||
147 | } else { |
||
148 | throw new NotFoundHttpException( |
||
149 | 'Controller method [' . $action . '] not found for ' . get_class($this) |
||
150 | ); |
||
151 | } |
||
152 | } |
||
153 | |||
154 | throw new NotFoundHttpException('No action specified for ' . get_class($this)); |
||
155 | } |
||
156 | |||
157 | /** |
||
158 | * @param $action |
||
159 | * @return bool |
||
160 | */ |
||
161 | protected function validAction($action) |
||
162 | { |
||
163 | return in_array($action, get_class_methods(get_class($this))); |
||
164 | } |
||
165 | |||
166 | /** |
||
167 | * Called before action |
||
168 | */ |
||
169 | protected function parseRequest() |
||
170 | { |
||
171 | return true; |
||
172 | } |
||
173 | |||
174 | /** |
||
175 | * Called before $this->action |
||
176 | */ |
||
177 | protected function beforeAction() |
||
178 | { |
||
179 | return true; |
||
180 | } |
||
181 | |||
182 | /** |
||
183 | * Called after $this->action |
||
184 | */ |
||
185 | protected function afterAction() |
||
186 | { |
||
187 | return true; |
||
188 | } |
||
189 | |||
190 | /** |
||
191 | * @param bool $action |
||
192 | * @param bool $controller |
||
193 | * @param bool $module |
||
194 | * @param array $params |
||
195 | * @return mixed |
||
196 | */ |
||
197 | public function call($action = false, $controller = false, $module = false, $params = []) |
||
198 | { |
||
199 | $newRequest = $this->getRequest()->duplicateWithParams($action, $controller, $module, $params); |
||
200 | |||
201 | $controller = $this->getDispatcher()->generateController($newRequest); |
||
202 | $controller = $this->prepareCallController($controller, $newRequest); |
||
0 ignored issues
–
show
It seems like
$controller can be null ; however, prepareCallController() does not accept null , maybe add an additional type check?
Unless you are absolutely sure that the expression can never be null because of other conditions, we strongly recommend to add an additional type check to your code: /** @return stdClass|null */
function mayReturnNull() { }
function doesNotAcceptNull(stdClass $x) { }
// With potential error.
function withoutCheck() {
$x = mayReturnNull();
doesNotAcceptNull($x); // Potential error here.
}
// Safe - Alternative 1
function withCheck1() {
$x = mayReturnNull();
if ( ! $x instanceof stdClass) {
throw new \LogicException('$x must be defined.');
}
doesNotAcceptNull($x);
}
// Safe - Alternative 2
function withCheck2() {
$x = mayReturnNull();
if ($x instanceof stdClass) {
doesNotAcceptNull($x);
}
}
![]() |
|||
203 | |||
204 | return call_user_func_array([$controller, $action], $params); |
||
205 | } |
||
206 | |||
207 | /** |
||
208 | * @param self $controller |
||
209 | * @param Request $newRequest |
||
210 | * @return Controller |
||
211 | */ |
||
212 | protected function prepareCallController($controller, $newRequest) |
||
213 | { |
||
214 | $controller->setRequest($newRequest); |
||
215 | $controller->populateFromRequest($newRequest); |
||
216 | |||
217 | return $controller; |
||
218 | } |
||
219 | |||
220 | /** |
||
221 | * @return string |
||
222 | */ |
||
223 | public function getAction() |
||
224 | { |
||
225 | return $this->action; |
||
226 | } |
||
227 | |||
228 | /** |
||
229 | * @param string $action |
||
230 | * @return self |
||
231 | */ |
||
232 | public function setAction($action) |
||
233 | { |
||
234 | $this->action = $action; |
||
235 | |||
236 | return $this; |
||
237 | } |
||
238 | |||
239 | /** |
||
240 | * @return string |
||
241 | */ |
||
242 | public function getRootNamespace() |
||
243 | { |
||
244 | return $this->getApplication()->getRootNamespace(); |
||
245 | } |
||
246 | |||
247 | /** |
||
248 | * @return Application |
||
249 | */ |
||
250 | public function getApplication() |
||
251 | { |
||
252 | return app('app'); |
||
253 | } |
||
254 | |||
255 | /** |
||
256 | * @param bool $action |
||
257 | * @param bool $controller |
||
258 | * @param bool $module |
||
259 | * @param array $params |
||
260 | */ |
||
261 | protected function forward($action = false, $controller = false, $module = false, $params = []) |
||
262 | { |
||
263 | $this->getDispatcher()->forward($action, $controller, $module, $params); |
||
264 | } |
||
265 | |||
266 | /** |
||
267 | * @param $message |
||
268 | * @param $url |
||
269 | * @param string $type |
||
270 | * @param bool $name |
||
271 | */ |
||
272 | protected function flashRedirect($message, $url, $type = 'success', $name = false) |
||
273 | { |
||
274 | $name = $name ? $name : $this->getName(); |
||
275 | app('flash.messages')->add($name, $type, $message); |
||
276 | $this->redirect($url); |
||
277 | } |
||
278 | |||
279 | /** |
||
280 | * @return string |
||
281 | */ |
||
282 | public function getName() |
||
283 | { |
||
284 | if ($this->name === null) { |
||
285 | $this->initName(); |
||
286 | } |
||
287 | |||
288 | return $this->name; |
||
289 | } |
||
290 | |||
291 | /** |
||
292 | * @param string $name |
||
293 | */ |
||
294 | public function setName($name) |
||
295 | { |
||
296 | $this->name = $name; |
||
297 | } |
||
298 | |||
299 | public function initName() |
||
300 | { |
||
301 | $this->setName($this->getFullName()); |
||
302 | } |
||
303 | |||
304 | /** |
||
305 | * @return string |
||
306 | */ |
||
307 | public function getFullName() |
||
308 | { |
||
309 | if ($this->fullName === null) { |
||
310 | $this->fullName = inflector()->unclassify($this->getClassName()); |
||
311 | } |
||
312 | |||
313 | return $this->fullName; |
||
314 | } |
||
315 | |||
316 | /** |
||
317 | * @param $url |
||
318 | * @param null $code |
||
319 | */ |
||
320 | protected function redirect($url, $code = null) |
||
321 | { |
||
322 | switch ($code) { |
||
323 | case '301': |
||
324 | header("HTTP/1.1 301 Moved Permanently"); |
||
325 | break; |
||
326 | } |
||
327 | header("Location: " . $url); |
||
328 | exit(); |
||
0 ignored issues
–
show
The method
redirect() contains an exit expression.
An exit expression should only be used in rare cases. For example, if you write a short command line script. In most cases however, using an ![]() |
|||
329 | } |
||
330 | } |
||
331 |
Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.
You can also find more detailed suggestions in the “Code” section of your repository.