‪TYPO3CMS  ‪main
StaticRouteResolver.php
Go to the documentation of this file.
1 <?php
2 
3 declare(strict_types=1);
4 
5 /*
6  * This file is part of the TYPO3 CMS project.
7  *
8  * It is free software; you can redistribute it and/or modify it under
9  * the terms of the GNU General Public License, either version 2
10  * of the License, or any later version.
11  *
12  * For the full copyright and license information, please read the
13  * LICENSE.txt file that was distributed with this source code.
14  *
15  * The TYPO3 project - inspiring people to share!
16  */
17 
19 
20 use Psr\Http\Message\ResponseInterface;
21 use Psr\Http\Message\ServerRequestInterface;
22 use Psr\Http\Server\MiddlewareInterface;
23 use Psr\Http\Server\RequestHandlerInterface;
32 
36 class ‪StaticRouteResolver implements MiddlewareInterface
37 {
38  public function ‪__construct(
39  protected readonly ‪RequestFactory $requestFactory,
40  protected readonly ‪LinkService $linkService
41  ) {
42  }
43 
47  public function ‪process(ServerRequestInterface $request, RequestHandlerInterface $handler): ResponseInterface
48  {
49  if (($site = $request->getAttribute('site')) instanceof ‪Site &&
50  ($configuration = $site->getConfiguration()['routes'] ?? null)
51  ) {
52  $path = ltrim($request->getUri()->getPath(), '/');
53  $routeConfig = $this->‪getApplicableStaticRoute($configuration, $site, $path);
54  if (is_array($routeConfig)) {
55  try {
56  [$content, $contentType] = $this->‪resolveByType($request, $site, $routeConfig['type'], $routeConfig);
58  return new ‪Response('Invalid route', 404, ['Content-Type' => 'text/plain']);
59  }
60 
61  return new ‪HtmlResponse($content, 200, ['Content-Type' => $contentType]);
62  }
63  }
64  return $handler->handle($request);
65  }
66 
77  protected function ‪getApplicableStaticRoute(array $staticRouteConfiguration, ‪Site $site, string $uriPath): ?array
78  {
79  $routeNames = array_map(static function (?string $route) use ($site) {
80  if ($route === null || $route === '') {
81  return null;
82  }
83  return ltrim(trim($site->‪getBase()->getPath(), '/') . '/' . ltrim($route, '/'), '/');
84  }, array_column($staticRouteConfiguration, 'route'));
85  // Remove empty routes which would throw an error (could happen within creating a false route in the GUI)
86  $routeNames = array_filter($routeNames);
87 
88  if (in_array($uriPath, $routeNames, true)) {
89  $key = array_search($uriPath, $routeNames, true);
90  // Only allow routes with a type "given"
91  if (isset($staticRouteConfiguration[$key]['type'])) {
92  return $staticRouteConfiguration[$key];
93  }
94  }
95  return null;
96  }
97 
98  protected function ‪getFromFile(‪File $file): array
99  {
100  $content = $file->‪getContents();
101  $contentType = $file->‪getMimeType();
102  return [$content, $contentType];
103  }
104 
105  protected function ‪getFromUri(string $uri): array
106  {
107  $response = $this->requestFactory->request($uri);
108  $contentType = 'text/plain; charset=utf-8';
109  $content = '';
110  if ($response->getStatusCode() === 200) {
111  $content = $response->getBody()->getContents();
112  $contentType = $response->getHeader('Content-Type');
113  }
114 
115  return [$content, $contentType];
116  }
117 
118  protected function ‪getPageUri(ServerRequestInterface $request, ‪Site $site, array $urlParams): string
119  {
120  $parameters = [];
121  // Add additional parameters, if set via TypoLink
122  if (isset($urlParams['parameters'])) {
123  parse_str($urlParams['parameters'], $parameters);
124  }
125  $parameters['type'] = $urlParams['pagetype'] ?? 0;
126  $parameters['_language'] = $request->getAttribute('language', null);
127  $uri = $site->‪getRouter()->generateUri(
128  (int)($urlParams['pageuid'] ?? 0),
129  $parameters,
130  '',
132  );
133  return (string)$uri;
134  }
135 
139  protected function ‪resolveByType(ServerRequestInterface $request, ‪Site $site, string $type, array $routeConfig): array
140  {
141  switch ($type) {
142  case 'staticText':
143  $content = $routeConfig['content'];
144  $contentType = 'text/plain; charset=utf-8';
145  break;
146  case 'uri':
147  $urlParams = $this->linkService->resolve($routeConfig['source']);
148  if ($urlParams['type'] === 'url' || $urlParams['type'] === 'page') {
149  $uri = $urlParams['url'] ?? $this->‪getPageUri($request, $site, $urlParams);
150  [$content, $contentType] = $this->‪getFromUri($uri);
151  } elseif ($urlParams['type'] === 'file') {
152  [$content, $contentType] = $this->‪getFromFile($urlParams['file']);
153  } else {
154  throw new \InvalidArgumentException('Can only handle URIs of type page, url or file.', 1537348076);
155  }
156 
157  break;
158  default:
159  throw new \InvalidArgumentException(
160  'Can only handle static file configurations with type uri or staticText.',
161  1537348083
162  );
163  }
164  return [$content, $contentType];
165  }
166 }
‪TYPO3\CMS\Core\Routing\RouterInterface
Definition: RouterInterface.php:28
‪TYPO3\CMS\Frontend\Middleware\StaticRouteResolver
Definition: StaticRouteResolver.php:37
‪TYPO3\CMS\Core\Resource\File\getContents
‪getContents()
Definition: File.php:104
‪TYPO3\CMS\Core\Site\Entity\Site
Definition: Site.php:42
‪TYPO3\CMS\Frontend\Middleware\StaticRouteResolver\getApplicableStaticRoute
‪array null getApplicableStaticRoute(array $staticRouteConfiguration, Site $site, string $uriPath)
Definition: StaticRouteResolver.php:77
‪TYPO3\CMS\Core\Http\Response
Definition: Response.php:32
‪TYPO3\CMS\Frontend\Middleware
Definition: BackendUserAuthenticator.php:18
‪TYPO3\CMS\Frontend\Middleware\StaticRouteResolver\getPageUri
‪getPageUri(ServerRequestInterface $request, Site $site, array $urlParams)
Definition: StaticRouteResolver.php:118
‪TYPO3\CMS\Core\Resource\File
Definition: File.php:26
‪TYPO3\CMS\Core\Routing\InvalidRouteArgumentsException
Definition: InvalidRouteArgumentsException.php:26
‪TYPO3\CMS\Frontend\Middleware\StaticRouteResolver\resolveByType
‪resolveByType(ServerRequestInterface $request, Site $site, string $type, array $routeConfig)
Definition: StaticRouteResolver.php:139
‪TYPO3\CMS\Core\Resource\AbstractFile\getMimeType
‪non empty string getMimeType()
Definition: AbstractFile.php:250
‪TYPO3\CMS\Core\Http\RequestFactory
Definition: RequestFactory.php:30
‪TYPO3\CMS\Frontend\Middleware\StaticRouteResolver\getFromFile
‪getFromFile(File $file)
Definition: StaticRouteResolver.php:98
‪TYPO3\CMS\Frontend\Middleware\StaticRouteResolver\__construct
‪__construct(protected readonly RequestFactory $requestFactory, protected readonly LinkService $linkService)
Definition: StaticRouteResolver.php:38
‪TYPO3\CMS\Frontend\Middleware\StaticRouteResolver\process
‪process(ServerRequestInterface $request, RequestHandlerInterface $handler)
Definition: StaticRouteResolver.php:47
‪TYPO3\CMS\Core\Routing\RouterInterface\ABSOLUTE_URL
‪const ABSOLUTE_URL
Definition: RouterInterface.php:32
‪TYPO3\CMS\Frontend\Middleware\StaticRouteResolver\getFromUri
‪getFromUri(string $uri)
Definition: StaticRouteResolver.php:105
‪TYPO3\CMS\Core\Site\Entity\Site\getRouter
‪getRouter(Context $context=null)
Definition: Site.php:348
‪TYPO3\CMS\Core\Http\HtmlResponse
Definition: HtmlResponse.php:28
‪TYPO3\CMS\Core\Site\Entity\Site\getBase
‪getBase()
Definition: Site.php:181