2 declare(strict_types
= 1);
4 namespace TYPO3\CMS\Core\Routing
;
7 * This file is part of the TYPO3 CMS project.
9 * It is free software; you can redistribute it and/or modify it under
10 * the terms of the GNU General Public License, either version 2
11 * of the License, or any later version.
13 * For the full copyright and license information, please read the
14 * LICENSE.txt file that was distributed with this source code.
16 * The TYPO3 project - inspiring people to share!
19 use Symfony\Component\Routing\CompiledRoute
;
20 use Symfony\Component\Routing\Route
as SymfonyRoute
;
21 use TYPO3\CMS\Core\Routing\Aspect\AspectInterface
;
22 use TYPO3\CMS\Core\Routing\Enhancer\EnhancerInterface
;
25 * TYPO3's route is built on top of Symfony's route with some special handling
26 * of "Aspects" built on top of a route
28 * @internal as this is tightly coupled to Symfony's Routing and we try to encapsulate this, please note that this might change if we change the under-the-hood implementation.
30 class Route
extends SymfonyRoute
34 * @var CompiledRoute|null
39 * @var AspectInterface[]
41 protected $aspects = [];
43 public function __construct(
46 array $requirements = [],
51 ?
string $condition = '',
54 parent
::__construct($path, $defaults, $requirements, $options, $host, $schemes, $methods, $condition);
55 $this->setAspects($aspects);
60 * @todo '_arguments' are added implicitly, make it explicit in enhancers
62 public function getArguments(): array
64 return $this->getOption('_arguments') ??
[];
68 * @return EnhancerInterface|null
70 public function getEnhancer(): ?EnhancerInterface
72 return $this->getOption('_enhancer') ?? null
;
76 * Returns all aspects.
78 * @return array The aspects
80 public function getAspects(): array
82 return $this->aspects
;
86 * Sets the aspects and removes existing ones.
88 * This method implements a fluent interface.
90 * @param array $aspects The aspects
93 public function setAspects(array $aspects): self
96 return $this->addAspects($aspects);
100 * Adds aspects to the existing maps.
102 * This method implements a fluent interface.
104 * @param array $aspects The aspects
107 public function addAspects(array $aspects): self
109 foreach ($aspects as $key => $aspect) {
110 if (isset($this->aspects
[$key])) {
111 throw new \
OverflowException(
112 sprintf('Cannot override aspect %s', $key),
116 $this->aspects
[$key] = $aspect;
118 $this->compiled
= null
;
123 * Returns the aspect for the given key.
125 * @param string $key The key
126 * @return AspectInterface|null The regex or null when not given
128 public function getAspect(string $key): ?AspectInterface
130 return $this->aspects
[$key] ?? null
;
134 * Checks if an aspect is set for the given key.
136 * @param string $key A variable name
137 * @return bool true if an aspect is specified, false otherwise
139 public function hasAspect(string $key): bool
141 return array_key_exists($key, $this->aspects
);
145 * Sets an aspect for the given key.
147 * @param string $key The key
148 * @param AspectInterface $aspect
151 public function setAspect(string $key, AspectInterface
$aspect): self
153 $this->aspects
[$key] = $aspect;
154 $this->compiled
= null
;
159 * @param string[] $classNames All (logical AND) class names that must match
160 * (including interfaces, abstract classes and traits)
161 * @param string[] $variableNames Variable names to be filtered
162 * @return AspectInterface[]
164 public function filterAspects(array $classNames, array $variableNames = []): array
166 $aspects = $this->aspects
;
167 if (empty($classNames) && empty($variableNames)) {
170 if (!empty($variableNames)) {
171 $aspects = array_filter(
173 function (string $variableName) use ($variableNames) {
174 return in_array($variableName, $variableNames, true
);
181 function (AspectInterface
$aspect) use ($classNames) {
182 $uses = class_uses($aspect);
183 foreach ($classNames as $className) {
184 if (!is_a($aspect, $className)
185 && !in_array($className, $uses, true
)