GitHub Access Token became invalid

It seems like the GitHub access token used for retrieving details about this repository from GitHub became invalid. This might prevent certain types of inspections from being run (in particular, everything related to pull requests).
Please ask an admin of your repository to re-new the access token on this website.
Completed
Pull Request — 3.x (#2576)
by
unknown
01:43
created

App::isHeadRequest()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 4

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
dl 0
loc 4
rs 10
c 0
b 0
f 0
cc 1
nc 1
nop 1
1
<?php
2
/**
3
 * Slim Framework (https://slimframework.com)
4
 *
5
 * @link      https://github.com/slimphp/Slim
6
 * @copyright Copyright (c) 2011-2017 Josh Lockhart
7
 * @license   https://github.com/slimphp/Slim/blob/3.x/LICENSE.md (MIT License)
8
 */
9
namespace Slim;
10
11
use Exception;
12
use Psr\Http\Message\UriInterface;
13
use Slim\Exception\InvalidMethodException;
14
use Slim\Http\Response;
15
use Throwable;
16
use Closure;
17
use InvalidArgumentException;
18
use Psr\Http\Message\RequestInterface;
19
use Psr\Http\Message\ServerRequestInterface;
20
use Psr\Http\Message\ResponseInterface;
21
use Psr\Container\ContainerInterface;
22
use FastRoute\Dispatcher;
23
use Slim\Exception\SlimException;
24
use Slim\Exception\MethodNotAllowedException;
25
use Slim\Exception\NotFoundException;
26
use Slim\Http\Uri;
27
use Slim\Http\Headers;
28
use Slim\Http\Body;
29
use Slim\Http\Request;
30
use Slim\Interfaces\Http\EnvironmentInterface;
31
use Slim\Interfaces\RouteGroupInterface;
32
use Slim\Interfaces\RouteInterface;
33
use Slim\Interfaces\RouterInterface;
34
35
/**
36
 * App
37
 *
38
 * This is the primary class with which you instantiate,
39
 * configure, and run a Slim Framework application.
40
 * The \Slim\App class also accepts Slim Framework middleware.
41
 *
42
 * @property-read callable $errorHandler
43
 * @property-read callable $phpErrorHandler
44
 * @property-read callable $notFoundHandler function($request, $response)
45
 * @property-read callable $notAllowedHandler function($request, $response, $allowedHttpMethods)
46
 */
47
class App
48
{
49
    use MiddlewareAwareTrait;
50
51
    /**
52
     * Current version
53
     *
54
     * @var string
55
     */
56
    const VERSION = '3.12.1-dev';
57
58
    /**
59
     * Container
60
     *
61
     * @var ContainerInterface
62
     */
63
    private $container;
64
65
    /********************************************************************************
66
     * Constructor
67
     *******************************************************************************/
68
69
    /**
70
     * Create new application
71
     *
72
     * @param ContainerInterface|array $container Either a ContainerInterface or an associative array of app settings
73
     * @throws InvalidArgumentException when no container is provided that implements ContainerInterface
74
     */
75
    public function __construct($container = [])
76
    {
77
        if (is_array($container)) {
78
            $container = new Container($container);
79
        }
80
        if (!$container instanceof ContainerInterface) {
81
            throw new InvalidArgumentException('Expected a ContainerInterface');
82
        }
83
        $this->container = $container;
84
    }
85
86
    /**
87
     * Enable access to the DI container by consumers of $app
88
     *
89
     * @return ContainerInterface
90
     */
91
    public function getContainer()
92
    {
93
        return $this->container;
94
    }
95
96
    /**
97
     * Add middleware
98
     *
99
     * This method prepends new middleware to the app's middleware stack.
100
     *
101
     * @param  callable|string    $callable The callback routine
102
     *
103
     * @return static
104
     */
105
    public function add($callable)
106
    {
107
        return $this->addMiddleware(new DeferredCallable($callable, $this->container));
108
    }
109
110
    /**
111
     * Calling a non-existant method on App checks to see if there's an item
112
     * in the container that is callable and if so, calls it.
113
     *
114
     * @param  string $method
115
     * @param  array $args
116
     * @return mixed
117
     */
118
    public function __call($method, $args)
119
    {
120
        if ($this->container->has($method)) {
121
            $obj = $this->container->get($method);
122
            if (is_callable($obj)) {
123
                return call_user_func_array($obj, $args);
124
            }
125
        }
126
127
        throw new \BadMethodCallException("Method $method is not a valid method");
128
    }
129
130
    /********************************************************************************
131
     * Router proxy methods
132
     *******************************************************************************/
133
134
    /**
135
     * Add GET route
136
     *
137
     * @param  string $pattern  The route URI pattern
138
     * @param  callable|string  $callable The route callback routine
139
     *
140
     * @return \Slim\Interfaces\RouteInterface
141
     */
142
    public function get($pattern, $callable)
143
    {
144
        return $this->map(['GET'], $pattern, $callable);
145
    }
146
147
    /**
148
     * Add POST route
149
     *
150
     * @param  string $pattern  The route URI pattern
151
     * @param  callable|string  $callable The route callback routine
152
     *
153
     * @return \Slim\Interfaces\RouteInterface
154
     */
155
    public function post($pattern, $callable)
156
    {
157
        return $this->map(['POST'], $pattern, $callable);
158
    }
159
160
    /**
161
     * Add PUT route
162
     *
163
     * @param  string $pattern  The route URI pattern
164
     * @param  callable|string  $callable The route callback routine
165
     *
166
     * @return \Slim\Interfaces\RouteInterface
167
     */
168
    public function put($pattern, $callable)
169
    {
170
        return $this->map(['PUT'], $pattern, $callable);
171
    }
172
173
    /**
174
     * Add PATCH route
175
     *
176
     * @param  string $pattern  The route URI pattern
177
     * @param  callable|string  $callable The route callback routine
178
     *
179
     * @return \Slim\Interfaces\RouteInterface
180
     */
181
    public function patch($pattern, $callable)
182
    {
183
        return $this->map(['PATCH'], $pattern, $callable);
184
    }
185
186
    /**
187
     * Add DELETE route
188
     *
189
     * @param  string $pattern  The route URI pattern
190
     * @param  callable|string  $callable The route callback routine
191
     *
192
     * @return \Slim\Interfaces\RouteInterface
193
     */
194
    public function delete($pattern, $callable)
195
    {
196
        return $this->map(['DELETE'], $pattern, $callable);
197
    }
198
199
    /**
200
     * Add OPTIONS route
201
     *
202
     * @param  string $pattern  The route URI pattern
203
     * @param  callable|string  $callable The route callback routine
204
     *
205
     * @return \Slim\Interfaces\RouteInterface
206
     */
207
    public function options($pattern, $callable)
208
    {
209
        return $this->map(['OPTIONS'], $pattern, $callable);
210
    }
211
212
    /**
213
     * Add route for any HTTP method
214
     *
215
     * @param  string $pattern  The route URI pattern
216
     * @param  callable|string  $callable The route callback routine
217
     *
218
     * @return \Slim\Interfaces\RouteInterface
219
     */
220
    public function any($pattern, $callable)
221
    {
222
        return $this->map(['GET', 'POST', 'PUT', 'PATCH', 'DELETE', 'OPTIONS'], $pattern, $callable);
223
    }
224
225
    /**
226
     * Add route with multiple methods
227
     *
228
     * @param  string[] $methods  Numeric array of HTTP method names
229
     * @param  string   $pattern  The route URI pattern
230
     * @param  callable|string    $callable The route callback routine
231
     *
232
     * @return RouteInterface
233
     */
234
    public function map(array $methods, $pattern, $callable)
235
    {
236
        if ($callable instanceof Closure) {
237
            $callable = $callable->bindTo($this->container);
238
        }
239
240
        $route = $this->container->get('router')->map($methods, $pattern, $callable);
241
        if (is_callable([$route, 'setContainer'])) {
242
            $route->setContainer($this->container);
243
        }
244
245
        if (is_callable([$route, 'setOutputBuffering'])) {
246
            $route->setOutputBuffering($this->container->get('settings')['outputBuffering']);
247
        }
248
249
        return $route;
250
    }
251
252
    /**
253
     * Add a route that sends an HTTP redirect
254
     *
255
     * @param string              $from
256
     * @param string|UriInterface $to
257
     * @param int                 $status
258
     *
259
     * @return RouteInterface
260
     */
261
    public function redirect($from, $to, $status = 302)
262
    {
263
        $handler = function ($request, ResponseInterface $response) use ($to, $status) {
264
            return $response->withHeader('Location', (string)$to)->withStatus($status);
265
        };
266
267
        return $this->get($from, $handler);
268
    }
269
270
    /**
271
     * Route Groups
272
     *
273
     * This method accepts a route pattern and a callback. All route
274
     * declarations in the callback will be prepended by the group(s)
275
     * that it is in.
276
     *
277
     * @param string           $pattern
278
     * @param callable|Closure $callable
279
     *
280
     * @return RouteGroupInterface
281
     */
282
    public function group($pattern, $callable)
283
    {
284
        /** @var RouteGroup $group */
285
        $group = $this->container->get('router')->pushGroup($pattern, $callable);
286
        $group->setContainer($this->container);
287
        $group($this);
288
        $this->container->get('router')->popGroup();
289
        return $group;
290
    }
291
292
    /********************************************************************************
293
     * Runner
294
     *******************************************************************************/
295
296
    /**
297
     * Run application
298
     *
299
     * This method traverses the application middleware stack and then sends the
300
     * resultant Response object to the HTTP client.
301
     *
302
     * @param bool|false $silent
303
     * @return ResponseInterface
304
     *
305
     * @throws Exception
306
     * @throws MethodNotAllowedException
307
     * @throws NotFoundException
308
     */
309
    public function run($silent = false)
310
    {
311
        $response = $this->container->get('response');
312
313
        try {
314
            ob_start();
315
            $response = $this->process($this->container->get('request'), $response);
316
        } catch (InvalidMethodException $e) {
317
            $response = $this->processInvalidMethod($e->getRequest(), $response);
318
        } finally {
319
            $output = ob_get_clean();
320
        }
321
322
        if (!empty($output) && $response->getBody()->isWritable()) {
323
            $outputBuffering = $this->container->get('settings')['outputBuffering'];
324
            if ($outputBuffering === 'prepend') {
325
                // prepend output buffer content
326
                $body = new Http\Body(fopen('php://temp', 'r+'));
327
                $body->write($output . $response->getBody());
328
                $response = $response->withBody($body);
329
            } elseif ($outputBuffering === 'append') {
330
                // append output buffer content
331
                $response->getBody()->write($output);
332
            }
333
        }
334
335
        $response = $this->finalize($response);
336
337
        if (!$silent) {
338
            $this->respond($response);
339
        }
340
341
        return $response;
342
    }
343
344
    /**
345
     * Pull route info for a request with a bad method to decide whether to
346
     * return a not-found error (default) or a bad-method error, then run
347
     * the handler for that error, returning the resulting response.
348
     *
349
     * Used for cases where an incoming request has an unrecognized method,
350
     * rather than throwing an exception and not catching it all the way up.
351
     *
352
     * @param ServerRequestInterface $request
353
     * @param ResponseInterface $response
354
     * @return ResponseInterface
355
     */
356
    protected function processInvalidMethod(ServerRequestInterface $request, ResponseInterface $response)
357
    {
358
        $router = $this->container->get('router');
359 View Code Duplication
        if (is_callable([$request->getUri(), 'getBasePath']) && is_callable([$router, 'setBasePath'])) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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.

Loading history...
360
            $router->setBasePath($request->getUri()->getBasePath());
361
        }
362
363
        $request = $this->dispatchRouterAndPrepareRoute($request, $router);
364
        $routeInfo = $request->getAttribute('routeInfo', [RouterInterface::DISPATCH_STATUS => Dispatcher::NOT_FOUND]);
365
366
        if ($routeInfo[RouterInterface::DISPATCH_STATUS] === Dispatcher::METHOD_NOT_ALLOWED) {
367
            return $this->handleException(
368
                new MethodNotAllowedException($request, $response, $routeInfo[RouterInterface::ALLOWED_METHODS]),
369
                $request,
370
                $response
371
            );
372
        }
373
374
        return $this->handleException(new NotFoundException($request, $response), $request, $response);
375
    }
376
377
    /**
378
     * Process a request
379
     *
380
     * This method traverses the application middleware stack and then returns the
381
     * resultant Response object.
382
     *
383
     * @param ServerRequestInterface $request
384
     * @param ResponseInterface $response
385
     * @return ResponseInterface
386
     *
387
     * @throws Exception
388
     * @throws MethodNotAllowedException
389
     * @throws NotFoundException
390
     */
391
    public function process(ServerRequestInterface $request, ResponseInterface $response)
392
    {
393
        // Ensure basePath is set
394
        $router = $this->container->get('router');
395 View Code Duplication
        if (is_callable([$request->getUri(), 'getBasePath']) && is_callable([$router, 'setBasePath'])) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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.

Loading history...
396
            $router->setBasePath($request->getUri()->getBasePath());
397
        }
398
399
        // Dispatch the Router first if the setting for this is on
400
        if ($this->container->get('settings')['determineRouteBeforeAppMiddleware'] === true) {
401
            // Dispatch router (note: you won't be able to alter routes after this)
402
            $request = $this->dispatchRouterAndPrepareRoute($request, $router);
403
        }
404
405
        // Traverse middleware stack
406
        try {
407
            $response = $this->callMiddlewareStack($request, $response);
408
        } catch (Exception $e) {
409
            $response = $this->handleException($e, $request, $response);
410
        } catch (Throwable $e) {
0 ignored issues
show
Bug introduced by
The class Throwable does not exist. Is this class maybe located in a folder that is not analyzed, or in a newer version of your dependencies than listed in your composer.lock/composer.json?
Loading history...
411
            $response = $this->handlePhpError($e, $request, $response);
412
        }
413
414
        return $response;
415
    }
416
417
    /**
418
     * Send the response to the client
419
     *
420
     * @param ResponseInterface $response
421
     */
422
    public function respond(ResponseInterface $response)
423
    {
424
        // Send response
425
        if (!headers_sent()) {
426
            // Headers
427
            foreach ($response->getHeaders() as $name => $values) {
428
                $first = stripos($name, 'Set-Cookie') === 0 ? false : true;
429
                foreach ($values as $value) {
430
                    header(sprintf('%s: %s', $name, $value), $first);
431
                    $first = false;
432
                }
433
            }
434
435
            // Set the status _after_ the headers, because of PHP's "helpful" behavior with location headers.
436
            // See https://github.com/slimphp/Slim/issues/1730
437
438
            // Status
439
            header(sprintf(
440
                'HTTP/%s %s %s',
441
                $response->getProtocolVersion(),
442
                $response->getStatusCode(),
443
                $response->getReasonPhrase()
444
            ), true, $response->getStatusCode());
445
        }
446
447
        // Body
448
        $request = $this->container->get('request');
449
        if (!$this->isEmptyResponse($response) && !$this->isHeadRequest($request)) {
450
            $body = $response->getBody();
451
            if ($body->isSeekable()) {
452
                $body->rewind();
453
            }
454
            $settings       = $this->container->get('settings');
455
            $chunkSize      = $settings['responseChunkSize'];
456
457
            $contentLength  = $response->getHeaderLine('Content-Length');
458
            if (!$contentLength) {
459
                $contentLength = $body->getSize();
460
            }
461
462
463
            if (isset($contentLength)) {
464
                $amountToRead = $contentLength;
465
                while ($amountToRead > 0 && !$body->eof()) {
466
                    $data = $body->read(min((int)$chunkSize, (int)$amountToRead));
467
                    echo $data;
468
469
                    $amountToRead -= strlen($data);
470
471
                    if (connection_status() != CONNECTION_NORMAL) {
472
                        break;
473
                    }
474
                }
475
            } else {
476
                while (!$body->eof()) {
477
                    echo $body->read((int)$chunkSize);
478
                    if (connection_status() != CONNECTION_NORMAL) {
479
                        break;
480
                    }
481
                }
482
            }
483
        }
484
    }
485
486
    /**
487
     * Invoke application
488
     *
489
     * This method implements the middleware interface. It receives
490
     * Request and Response objects, and it returns a Response object
491
     * after compiling the routes registered in the Router and dispatching
492
     * the Request object to the appropriate Route callback routine.
493
     *
494
     * @param  ServerRequestInterface $request  The most recent Request object
495
     * @param  ResponseInterface      $response The most recent Response object
496
     *
497
     * @return ResponseInterface
498
     * @throws MethodNotAllowedException
499
     * @throws NotFoundException
500
     */
501
    public function __invoke(ServerRequestInterface $request, ResponseInterface $response)
502
    {
503
        // Get the route info
504
        $routeInfo = $request->getAttribute('routeInfo');
505
506
        /** @var \Slim\Interfaces\RouterInterface $router */
507
        $router = $this->container->get('router');
508
509
        // If router hasn't been dispatched or the URI changed then dispatch
510
        if (null === $routeInfo || ($routeInfo['request'] !== [$request->getMethod(), (string) $request->getUri()])) {
511
            $request = $this->dispatchRouterAndPrepareRoute($request, $router);
512
            $routeInfo = $request->getAttribute('routeInfo');
513
        }
514
515
        if ($routeInfo[0] === Dispatcher::FOUND) {
516
            $route = $router->lookupRoute($routeInfo[1]);
517
            return $route->run($request, $response);
518
        } elseif ($routeInfo[0] === Dispatcher::METHOD_NOT_ALLOWED) {
519
            if (!$this->container->has('notAllowedHandler')) {
520
                throw new MethodNotAllowedException($request, $response, $routeInfo[1]);
521
            }
522
            /** @var callable $notAllowedHandler */
523
            $notAllowedHandler = $this->container->get('notAllowedHandler');
524
            return $notAllowedHandler($request, $response, $routeInfo[1]);
525
        }
526
527
        if (!$this->container->has('notFoundHandler')) {
528
            throw new NotFoundException($request, $response);
529
        }
530
        /** @var callable $notFoundHandler */
531
        $notFoundHandler = $this->container->get('notFoundHandler');
532
        return $notFoundHandler($request, $response);
533
    }
534
535
    /**
536
     * Perform a sub-request from within an application route
537
     *
538
     * This method allows you to prepare and initiate a sub-request, run within
539
     * the context of the current request. This WILL NOT issue a remote HTTP
540
     * request. Instead, it will route the provided URL, method, headers,
541
     * cookies, body, and server variables against the set of registered
542
     * application routes. The result response object is returned.
543
     *
544
     * @param  string            $method      The request method (e.g., GET, POST, PUT, etc.)
545
     * @param  string            $path        The request URI path
546
     * @param  string            $query       The request URI query string
547
     * @param  array             $headers     The request headers (key-value array)
548
     * @param  array             $cookies     The request cookies (key-value array)
549
     * @param  string            $bodyContent The request body
550
     * @param  ResponseInterface $response     The response object (optional)
551
     * @return ResponseInterface
552
     */
553
    public function subRequest(
554
        $method,
555
        $path,
556
        $query = '',
557
        array $headers = [],
558
        array $cookies = [],
559
        $bodyContent = '',
560
        ResponseInterface $response = null
561
    ) {
562
        $env = $this->container->get('environment');
563
        $uri = Uri::createFromEnvironment($env)->withPath($path)->withQuery($query);
564
        $headers = new Headers($headers);
565
        $serverParams = $env->all();
566
        $body = new Body(fopen('php://temp', 'r+'));
567
        $body->write($bodyContent);
568
        $body->rewind();
569
        $request = new Request($method, $uri, $headers, $cookies, $serverParams, $body);
570
571
        if (!$response) {
572
            $response = $this->container->get('response');
573
        }
574
575
        return $this($request, $response);
576
    }
577
578
    /**
579
     * Dispatch the router to find the route. Prepare the route for use.
580
     *
581
     * @param ServerRequestInterface $request
582
     * @param RouterInterface        $router
583
     * @return ServerRequestInterface
584
     */
585
    protected function dispatchRouterAndPrepareRoute(ServerRequestInterface $request, RouterInterface $router)
586
    {
587
        $routeInfo = $router->dispatch($request);
588
589
        if ($routeInfo[0] === Dispatcher::FOUND) {
590
            $routeArguments = [];
591
            foreach ($routeInfo[2] as $k => $v) {
592
                $routeArguments[$k] = urldecode($v);
593
            }
594
595
            $route = $router->lookupRoute($routeInfo[1]);
596
            $route->prepare($request, $routeArguments);
597
598
            // add route to the request's attributes in case a middleware or handler needs access to the route
599
            $request = $request->withAttribute('route', $route);
600
        }
601
602
        $routeInfo['request'] = [$request->getMethod(), (string) $request->getUri()];
603
604
        return $request->withAttribute('routeInfo', $routeInfo);
605
    }
606
607
    /**
608
     * Finalize response
609
     *
610
     * @param ResponseInterface $response
611
     * @return ResponseInterface
612
     */
613
    protected function finalize(ResponseInterface $response)
614
    {
615
        // stop PHP sending a Content-Type automatically
616
        ini_set('default_mimetype', '');
617
618
        $request = $this->container->get('request');
619
        if ($this->isEmptyResponse($response) && !$this->isHeadRequest($request)) {
620
            return $response->withoutHeader('Content-Type')->withoutHeader('Content-Length');
621
        }
622
623
        // Add Content-Length header if `addContentLengthHeader` setting is set
624
        if (isset($this->container->get('settings')['addContentLengthHeader']) &&
625
            $this->container->get('settings')['addContentLengthHeader'] == true) {
626
            if (ob_get_length() > 0) {
627
                throw new \RuntimeException("Unexpected data in output buffer. " .
628
                    "Maybe you have characters before an opening <?php tag?");
629
            }
630
            $size = $response->getBody()->getSize();
631
            if ($size !== null && !$response->hasHeader('Content-Length')) {
632
                $response = $response->withHeader('Content-Length', (string) $size);
633
            }
634
        }
635
636
        return $response;
637
    }
638
639
    /**
640
     * Helper method, if the provided response must not output a body and false
641
     * if the response could have a body.
642
     *
643
     * @see https://tools.ietf.org/html/rfc7231
644
     *
645
     * @param ResponseInterface $response
646
     * @return bool
647
     */
648
    protected function isEmptyResponse(ResponseInterface $response)
649
    {
650
        if (method_exists($response, 'isEmpty')) {
651
            return $response->isEmpty();
652
        }
653
654
        return in_array($response->getStatusCode(), [204, 205, 304]);
655
    }
656
657
    /**
658
     * Helper method to check if the current request is a HEAD request
659
     *
660
     * @param RequestInterface $request
661
     *
662
     * @return bool
663
     */
664
    protected function isHeadRequest(RequestInterface $request)
665
    {
666
        return strtoupper($request->getMethod()) === 'HEAD';
667
    }
668
669
    /**
670
     * Call relevant handler from the Container if needed. If it doesn't exist,
671
     * then just re-throw.
672
     *
673
     * @param  Exception $e
674
     * @param  ServerRequestInterface $request
675
     * @param  ResponseInterface $response
676
     *
677
     * @return ResponseInterface
678
     * @throws Exception if a handler is needed and not found
679
     */
680
    protected function handleException(Exception $e, ServerRequestInterface $request, ResponseInterface $response)
681
    {
682
        if ($e instanceof MethodNotAllowedException) {
683
            $handler = 'notAllowedHandler';
684
            $params = [$e->getRequest(), $e->getResponse(), $e->getAllowedMethods()];
685
        } elseif ($e instanceof NotFoundException) {
686
            $handler = 'notFoundHandler';
687
            $params = [$e->getRequest(), $e->getResponse(), $e];
688
        } elseif ($e instanceof SlimException) {
689
            // This is a Stop exception and contains the response
690
            return $e->getResponse();
691
        } else {
692
            // Other exception, use $request and $response params
693
            $handler = 'errorHandler';
694
            $params = [$request, $response, $e];
695
        }
696
697 View Code Duplication
        if ($this->container->has($handler)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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.

Loading history...
698
            $callable = $this->container->get($handler);
699
            // Call the registered handler
700
            return call_user_func_array($callable, $params);
701
        }
702
703
        // No handlers found, so just throw the exception
704
        throw $e;
705
    }
706
707
    /**
708
     * Call relevant handler from the Container if needed. If it doesn't exist,
709
     * then just re-throw.
710
     *
711
     * @param  Throwable $e
712
     * @param  ServerRequestInterface $request
713
     * @param  ResponseInterface $response
714
     * @return ResponseInterface
715
     * @throws Throwable
716
     */
717
    protected function handlePhpError(Throwable $e, ServerRequestInterface $request, ResponseInterface $response)
718
    {
719
        $handler = 'phpErrorHandler';
720
        $params = [$request, $response, $e];
721
722 View Code Duplication
        if ($this->container->has($handler)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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.

Loading history...
723
            $callable = $this->container->get($handler);
724
            // Call the registered handler
725
            return call_user_func_array($callable, $params);
726
        }
727
728
        // No handlers found, so just throw the exception
729
        throw $e;
730
    }
731
}
732