[ Index ]

PHP Cross Reference of phpBB-3.3.14-deutsch

title

Body

[close]

/vendor/symfony/http-kernel/ -> HttpKernel.php (source)

   1  <?php
   2  
   3  /*
   4   * This file is part of the Symfony package.
   5   *
   6   * (c) Fabien Potencier <fabien@symfony.com>
   7   *
   8   * For the full copyright and license information, please view the LICENSE
   9   * file that was distributed with this source code.
  10   */
  11  
  12  namespace Symfony\Component\HttpKernel;
  13  
  14  use Symfony\Component\EventDispatcher\EventDispatcherInterface;
  15  use Symfony\Component\HttpFoundation\Exception\RequestExceptionInterface;
  16  use Symfony\Component\HttpFoundation\Request;
  17  use Symfony\Component\HttpFoundation\RequestStack;
  18  use Symfony\Component\HttpFoundation\Response;
  19  use Symfony\Component\HttpKernel\Controller\ArgumentResolver;
  20  use Symfony\Component\HttpKernel\Controller\ArgumentResolverInterface;
  21  use Symfony\Component\HttpKernel\Controller\ControllerResolverInterface;
  22  use Symfony\Component\HttpKernel\Event\FilterControllerArgumentsEvent;
  23  use Symfony\Component\HttpKernel\Event\FilterControllerEvent;
  24  use Symfony\Component\HttpKernel\Event\FilterResponseEvent;
  25  use Symfony\Component\HttpKernel\Event\FinishRequestEvent;
  26  use Symfony\Component\HttpKernel\Event\GetResponseEvent;
  27  use Symfony\Component\HttpKernel\Event\GetResponseForControllerResultEvent;
  28  use Symfony\Component\HttpKernel\Event\GetResponseForExceptionEvent;
  29  use Symfony\Component\HttpKernel\Event\PostResponseEvent;
  30  use Symfony\Component\HttpKernel\Exception\BadRequestHttpException;
  31  use Symfony\Component\HttpKernel\Exception\HttpExceptionInterface;
  32  use Symfony\Component\HttpKernel\Exception\NotFoundHttpException;
  33  
  34  /**
  35   * HttpKernel notifies events to convert a Request object to a Response one.
  36   *
  37   * @author Fabien Potencier <fabien@symfony.com>
  38   */
  39  class HttpKernel implements HttpKernelInterface, TerminableInterface
  40  {
  41      protected $dispatcher;
  42      protected $resolver;
  43      protected $requestStack;
  44      private $argumentResolver;
  45  
  46      public function __construct(EventDispatcherInterface $dispatcher, ControllerResolverInterface $resolver, RequestStack $requestStack = null, ArgumentResolverInterface $argumentResolver = null)
  47      {
  48          $this->dispatcher = $dispatcher;
  49          $this->resolver = $resolver;
  50          $this->requestStack = $requestStack ?: new RequestStack();
  51          $this->argumentResolver = $argumentResolver;
  52  
  53          if (null === $this->argumentResolver) {
  54              @trigger_error(sprintf('As of 3.1 an %s is used to resolve arguments. In 4.0 the $argumentResolver becomes the %s if no other is provided instead of using the $resolver argument.', ArgumentResolverInterface::class, ArgumentResolver::class), \E_USER_DEPRECATED);
  55              // fallback in case of deprecations
  56              $this->argumentResolver = $resolver;
  57          }
  58      }
  59  
  60      /**
  61       * {@inheritdoc}
  62       */
  63      public function handle(Request $request, $type = HttpKernelInterface::MASTER_REQUEST, $catch = true)
  64      {
  65          $request->headers->set('X-Php-Ob-Level', (string) ob_get_level());
  66  
  67          try {
  68              return $this->handleRaw($request, $type);
  69          } catch (\Exception $e) {
  70              if ($e instanceof RequestExceptionInterface) {
  71                  $e = new BadRequestHttpException($e->getMessage(), $e);
  72              }
  73              if (false === $catch) {
  74                  $this->finishRequest($request, $type);
  75  
  76                  throw $e;
  77              }
  78  
  79              return $this->handleException($e, $request, $type);
  80          }
  81      }
  82  
  83      /**
  84       * {@inheritdoc}
  85       */
  86      public function terminate(Request $request, Response $response)
  87      {
  88          $this->dispatcher->dispatch(KernelEvents::TERMINATE, new PostResponseEvent($this, $request, $response));
  89      }
  90  
  91      /**
  92       * @internal
  93       */
  94      public function terminateWithException(\Exception $exception, Request $request = null)
  95      {
  96          if (!$request = $request ?: $this->requestStack->getMasterRequest()) {
  97              throw $exception;
  98          }
  99  
 100          $response = $this->handleException($exception, $request, self::MASTER_REQUEST);
 101  
 102          $response->sendHeaders();
 103          $response->sendContent();
 104  
 105          $this->terminate($request, $response);
 106      }
 107  
 108      /**
 109       * Handles a request to convert it to a response.
 110       *
 111       * Exceptions are not caught.
 112       *
 113       * @param Request $request A Request instance
 114       * @param int     $type    The type of the request (one of HttpKernelInterface::MASTER_REQUEST or HttpKernelInterface::SUB_REQUEST)
 115       *
 116       * @return Response A Response instance
 117       *
 118       * @throws \LogicException       If one of the listener does not behave as expected
 119       * @throws NotFoundHttpException When controller cannot be found
 120       */
 121      private function handleRaw(Request $request, $type = self::MASTER_REQUEST)
 122      {
 123          $this->requestStack->push($request);
 124  
 125          // request
 126          $event = new GetResponseEvent($this, $request, $type);
 127          $this->dispatcher->dispatch(KernelEvents::REQUEST, $event);
 128  
 129          if ($event->hasResponse()) {
 130              return $this->filterResponse($event->getResponse(), $request, $type);
 131          }
 132  
 133          // load controller
 134          if (false === $controller = $this->resolver->getController($request)) {
 135              throw new NotFoundHttpException(sprintf('Unable to find the controller for path "%s". The route is wrongly configured.', $request->getPathInfo()));
 136          }
 137  
 138          $event = new FilterControllerEvent($this, $controller, $request, $type);
 139          $this->dispatcher->dispatch(KernelEvents::CONTROLLER, $event);
 140          $controller = $event->getController();
 141  
 142          // controller arguments
 143          $arguments = $this->argumentResolver->getArguments($request, $controller);
 144  
 145          $event = new FilterControllerArgumentsEvent($this, $controller, $arguments, $request, $type);
 146          $this->dispatcher->dispatch(KernelEvents::CONTROLLER_ARGUMENTS, $event);
 147          $controller = $event->getController();
 148          $arguments = $event->getArguments();
 149  
 150          // call controller
 151          $response = \call_user_func_array($controller, $arguments);
 152  
 153          // view
 154          if (!$response instanceof Response) {
 155              $event = new GetResponseForControllerResultEvent($this, $request, $type, $response);
 156              $this->dispatcher->dispatch(KernelEvents::VIEW, $event);
 157  
 158              if ($event->hasResponse()) {
 159                  $response = $event->getResponse();
 160              }
 161  
 162              if (!$response instanceof Response) {
 163                  $msg = sprintf('The controller must return a response (%s given).', $this->varToString($response));
 164  
 165                  // the user may have forgotten to return something
 166                  if (null === $response) {
 167                      $msg .= ' Did you forget to add a return statement somewhere in your controller?';
 168                  }
 169                  throw new \LogicException($msg);
 170              }
 171          }
 172  
 173          return $this->filterResponse($response, $request, $type);
 174      }
 175  
 176      /**
 177       * Filters a response object.
 178       *
 179       * @param Response $response A Response instance
 180       * @param Request  $request  An error message in case the response is not a Response object
 181       * @param int      $type     The type of the request (one of HttpKernelInterface::MASTER_REQUEST or HttpKernelInterface::SUB_REQUEST)
 182       *
 183       * @return Response The filtered Response instance
 184       *
 185       * @throws \RuntimeException if the passed object is not a Response instance
 186       */
 187      private function filterResponse(Response $response, Request $request, $type)
 188      {
 189          $event = new FilterResponseEvent($this, $request, $type, $response);
 190  
 191          $this->dispatcher->dispatch(KernelEvents::RESPONSE, $event);
 192  
 193          $this->finishRequest($request, $type);
 194  
 195          return $event->getResponse();
 196      }
 197  
 198      /**
 199       * Publishes the finish request event, then pop the request from the stack.
 200       *
 201       * Note that the order of the operations is important here, otherwise
 202       * operations such as {@link RequestStack::getParentRequest()} can lead to
 203       * weird results.
 204       *
 205       * @param int $type
 206       */
 207      private function finishRequest(Request $request, $type)
 208      {
 209          $this->dispatcher->dispatch(KernelEvents::FINISH_REQUEST, new FinishRequestEvent($this, $request, $type));
 210          $this->requestStack->pop();
 211      }
 212  
 213      /**
 214       * Handles an exception by trying to convert it to a Response.
 215       *
 216       * @param \Exception $e       An \Exception instance
 217       * @param Request    $request A Request instance
 218       * @param int        $type    The type of the request
 219       *
 220       * @return Response A Response instance
 221       *
 222       * @throws \Exception
 223       */
 224      private function handleException(\Exception $e, $request, $type)
 225      {
 226          $event = new GetResponseForExceptionEvent($this, $request, $type, $e);
 227          $this->dispatcher->dispatch(KernelEvents::EXCEPTION, $event);
 228  
 229          // a listener might have replaced the exception
 230          $e = $event->getException();
 231  
 232          if (!$event->hasResponse()) {
 233              $this->finishRequest($request, $type);
 234  
 235              throw $e;
 236          }
 237  
 238          $response = $event->getResponse();
 239  
 240          // the developer asked for a specific status code
 241          if ($response->headers->has('X-Status-Code')) {
 242              @trigger_error(sprintf('Using the X-Status-Code header is deprecated since Symfony 3.3 and will be removed in 4.0. Use %s::allowCustomResponseCode() instead.', GetResponseForExceptionEvent::class), \E_USER_DEPRECATED);
 243  
 244              $response->setStatusCode($response->headers->get('X-Status-Code'));
 245  
 246              $response->headers->remove('X-Status-Code');
 247          } elseif (!$event->isAllowingCustomResponseCode() && !$response->isClientError() && !$response->isServerError() && !$response->isRedirect()) {
 248              // ensure that we actually have an error response
 249              if ($e instanceof HttpExceptionInterface) {
 250                  // keep the HTTP status code and headers
 251                  $response->setStatusCode($e->getStatusCode());
 252                  $response->headers->add($e->getHeaders());
 253              } else {
 254                  $response->setStatusCode(500);
 255              }
 256          }
 257  
 258          try {
 259              return $this->filterResponse($response, $request, $type);
 260          } catch (\Exception $e) {
 261              return $response;
 262          }
 263      }
 264  
 265      /**
 266       * Returns a human-readable string for the specified variable.
 267       */
 268      private function varToString($var)
 269      {
 270          if (\is_object($var)) {
 271              return sprintf('Object(%s)', \get_class($var));
 272          }
 273  
 274          if (\is_array($var)) {
 275              $a = [];
 276              foreach ($var as $k => $v) {
 277                  $a[] = sprintf('%s => %s', $k, $this->varToString($v));
 278              }
 279  
 280              return sprintf('Array(%s)', implode(', ', $a));
 281          }
 282  
 283          if (\is_resource($var)) {
 284              return sprintf('Resource(%s)', get_resource_type($var));
 285          }
 286  
 287          if (null === $var) {
 288              return 'null';
 289          }
 290  
 291          if (false === $var) {
 292              return 'false';
 293          }
 294  
 295          if (true === $var) {
 296              return 'true';
 297          }
 298  
 299          return (string) $var;
 300      }
 301  }


Generated: Mon Nov 25 19:05:08 2024 Cross-referenced by PHPXref 0.7.1