Skip to content

Navigation Menu

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Appearance settings

[FrameworkBundle] Add --method option to debug:router command #59909

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions 1 src/Symfony/Bundle/FrameworkBundle/CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ CHANGELOG
* Add `framework.validation.disable_translation` option
* Add support for signal plain name in the `messenger.stop_worker_on_signals` configuration
* Deprecate the `framework.validation.cache` option
* Add `--method` option to the `debug:router` command

7.2
---
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -55,6 +55,7 @@ protected function configure(): void
new InputOption('show-aliases', null, InputOption::VALUE_NONE, 'Show aliases in overview'),
new InputOption('format', null, InputOption::VALUE_REQUIRED, \sprintf('The output format ("%s")', implode('", "', $this->getAvailableFormatOptions())), 'txt'),
new InputOption('raw', null, InputOption::VALUE_NONE, 'To output raw route(s)'),
new InputOption('method', null, InputOption::VALUE_REQUIRED, 'Filter by HTTP method', '', ['GET', 'POST', 'PUT', 'DELETE', 'PATCH']),
])
->setHelp(<<<'EOF'
The <info>%command.name%</info> displays the configured routes:
Expand All @@ -76,6 +77,7 @@ protected function execute(InputInterface $input, OutputInterface $output): int
{
$io = new SymfonyStyle($input, $output);
$name = $input->getArgument('name');
$method = strtoupper($input->getOption('method'));
$helper = new DescriptorHelper($this->fileLinkFormatter);
$routes = $this->router->getRouteCollection();
$container = null;
Expand All @@ -85,7 +87,7 @@ protected function execute(InputInterface $input, OutputInterface $output): int

if ($name) {
$route = $routes->get($name);
$matchingRoutes = $this->findRouteNameContaining($name, $routes);
$matchingRoutes = $this->findRouteNameContaining($name, $routes, $method);

if (!$input->isInteractive() && !$route && \count($matchingRoutes) > 1) {
$helper->describe($io, $this->findRouteContaining($name, $routes), [
Expand All @@ -94,6 +96,7 @@ protected function execute(InputInterface $input, OutputInterface $output): int
'show_controllers' => $input->getOption('show-controllers'),
'show_aliases' => $input->getOption('show-aliases'),
'output' => $io,
'method' => $method,
]);

return 0;
Expand Down Expand Up @@ -124,17 +127,18 @@ protected function execute(InputInterface $input, OutputInterface $output): int
'show_aliases' => $input->getOption('show-aliases'),
'output' => $io,
'container' => $container,
'method' => $method,
]);
}

return 0;
}

private function findRouteNameContaining(string $name, RouteCollection $routes): array
private function findRouteNameContaining(string $name, RouteCollection $routes, string $method): array
{
$foundRoutesNames = [];
foreach ($routes as $routeName => $route) {
if (false !== stripos($routeName, $name)) {
if (false !== stripos($routeName, $name) && (!$method || !$route->getMethods() || \in_array($method, $route->getMethods(), true))) {
$foundRoutesNames[] = $routeName;
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ public function describe(OutputInterface $output, mixed $object, array $options
}

match (true) {
$object instanceof RouteCollection => $this->describeRouteCollection($object, $options),
$object instanceof RouteCollection => $this->describeRouteCollection($this->filterRoutesByHttpMethod($object, $options['method'] ?? ''), $options),
$object instanceof Route => $this->describeRoute($object, $options),
$object instanceof ParameterBag => $this->describeContainerParameters($object, $options),
$object instanceof ContainerBuilder && !empty($options['env-vars']) => $this->describeContainerEnvVars($this->getContainerEnvVars($object), $options),
Expand Down Expand Up @@ -360,4 +360,20 @@ protected function getServiceEdges(ContainerBuilder $container, string $serviceI
return [];
}
}

private function filterRoutesByHttpMethod(RouteCollection $routes, string $method): RouteCollection
{
if (!$method) {
return $routes;
}
$filteredRoutes = clone $routes;

foreach ($filteredRoutes as $routeName => $route) {
if ($route->getMethods() && !\in_array($method, $route->getMethods(), true)) {
$filteredRoutes->remove($routeName);
}
}

return $filteredRoutes;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,21 @@ public static function getDescribeRouteCollectionTestData(): array
return static::getDescriptionTestData(ObjectsProvider::getRouteCollections());
}

/** @dataProvider getDescribeRouteCollectionWithHttpMethodFilterTestData */
public function testDescribeRouteCollectionWithHttpMethodFilter(string $httpMethod, RouteCollection $routes, $expectedDescription)
{
$this->assertDescription($expectedDescription, $routes, ['method' => $httpMethod]);
}

public static function getDescribeRouteCollectionWithHttpMethodFilterTestData(): iterable
{
foreach (ObjectsProvider::getRouteCollectionsByHttpMethod() as $httpMethod => $routeCollection) {
foreach (static::getDescriptionTestData($routeCollection) as $testData) {
yield [$httpMethod, ...$testData];
}
}
}

/** @dataProvider getDescribeRouteTestData */
public function testDescribeRoute(Route $route, $expectedDescription)
{
Expand Down Expand Up @@ -273,6 +288,7 @@ private function assertDescription($expectedDescription, $describedObject, array
$options['is_debug'] = false;
$options['raw_output'] = true;
$options['raw_text'] = true;
$options['method'] ??= null;
$output = new BufferedOutput(BufferedOutput::VERBOSITY_NORMAL, true);

if ('txt' === $this->getFormat()) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,38 @@ public static function getRouteCollections()
return ['route_collection_1' => $collection1];
}

public static function getRouteCollectionsByHttpMethod(): array
{
$collection = new RouteCollection();
foreach (self::getRoutes() as $name => $route) {
$collection->add($name, $route);
}

// Clone the original collection and add a route without any specific method restrictions
$collectionWithRouteWithoutMethodRestriction = clone $collection;
$collectionWithRouteWithoutMethodRestriction->add(
'route_3',
new RouteStub(
'/other/route',
[],
[],
['opt1' => 'val1', 'opt2' => 'val2'],
'localhost',
['http', 'https'],
[],
)
);

return [
'GET' => [
'route_collection_2' => $collectionWithRouteWithoutMethodRestriction,
],
'PUT' => [
nicolas-grekas marked this conversation as resolved.
Show resolved Hide resolved
'route_collection_3' => $collection,
],
];
}

public static function getRoutes()
{
return [
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
{
"route_1": {
"path": "\/hello\/{name}",
"pathRegex": "#PATH_REGEX#",
"host": "localhost",
"hostRegex": "#HOST_REGEX#",
"scheme": "http|https",
"method": "GET|HEAD",
"class": "Symfony\\Bundle\\FrameworkBundle\\Tests\\Console\\Descriptor\\RouteStub",
"defaults": {
"name": "Joseph"
},
"requirements": {
"name": "[a-z]+"
},
"options": {
"compiler_class": "Symfony\\Component\\Routing\\RouteCompiler",
"opt1": "val1",
"opt2": "val2"
}
},
"route_3": {
"path": "\/other\/route",
"pathRegex": "#PATH_REGEX#",
"host": "localhost",
"hostRegex": "#HOST_REGEX#",
"scheme": "http|https",
"method": "ANY",
"class": "Symfony\\Bundle\\FrameworkBundle\\Tests\\Console\\Descriptor\\RouteStub",
"defaults": [],
"requirements": "NO CUSTOM",
"options": {
"compiler_class": "Symfony\\Component\\Routing\\RouteCompiler",
"opt1": "val1",
"opt2": "val2"
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
route_1
-------

- Path: /hello/{name}
- Path Regex: #PATH_REGEX#
- Host: localhost
- Host Regex: #HOST_REGEX#
- Scheme: http|https
- Method: GET|HEAD
- Class: Symfony\Bundle\FrameworkBundle\Tests\Console\Descriptor\RouteStub
- Defaults:
- `name`: Joseph
- Requirements:
- `name`: [a-z]+
- Options:
- `compiler_class`: Symfony\Component\Routing\RouteCompiler
- `opt1`: val1
- `opt2`: val2


route_3
-------

- Path: /other/route
- Path Regex: #PATH_REGEX#
- Host: localhost
- Host Regex: #HOST_REGEX#
- Scheme: http|https
- Method: ANY
- Class: Symfony\Bundle\FrameworkBundle\Tests\Console\Descriptor\RouteStub
- Defaults: NONE
- Requirements: NO CUSTOM
- Options:
- `compiler_class`: Symfony\Component\Routing\RouteCompiler
- `opt1`: val1
- `opt2`: val2

Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
--------- ---------- ------------ ----------- ---------------
 Name   Method   Scheme   Host   Path 
--------- ---------- ------------ ----------- ---------------
route_1 GET|HEAD http|https localhost /hello/{name}
route_3 ANY http|https localhost /other/route
--------- ---------- ------------ ----------- ---------------

Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
<?xml version="1.0" encoding="UTF-8"?>
<routes>
<route name="route_1" class="Symfony\Bundle\FrameworkBundle\Tests\Console\Descriptor\RouteStub">
<path regex="#PATH_REGEX#">/hello/{name}</path>
<host regex="#HOST_REGEX#">localhost</host>
<scheme>http</scheme>
<scheme>https</scheme>
<method>GET</method>
<method>HEAD</method>
<defaults>
<default key="name">Joseph</default>
</defaults>
<requirements>
<requirement key="name">[a-z]+</requirement>
</requirements>
<options>
<option key="compiler_class">Symfony\Component\Routing\RouteCompiler</option>
<option key="opt1">val1</option>
<option key="opt2">val2</option>
</options>
</route>
<route name="route_3" class="Symfony\Bundle\FrameworkBundle\Tests\Console\Descriptor\RouteStub">
<path regex="#PATH_REGEX#">/other/route</path>
<host regex="#HOST_REGEX#">localhost</host>
<scheme>http</scheme>
<scheme>https</scheme>
<options>
<option key="compiler_class">Symfony\Component\Routing\RouteCompiler</option>
<option key="opt1">val1</option>
<option key="opt2">val2</option>
</options>
</route>
</routes>
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
{
"route_2": {
"path": "\/name\/add",
"pathRegex": "#PATH_REGEX#",
"host": "localhost",
"hostRegex": "#HOST_REGEX#",
"scheme": "http|https",
"method": "PUT|POST",
"class": "Symfony\\Bundle\\FrameworkBundle\\Tests\\Console\\Descriptor\\RouteStub",
"defaults": [],
"requirements": "NO CUSTOM",
"options": {
"compiler_class": "Symfony\\Component\\Routing\\RouteCompiler",
"opt1": "val1",
"opt2": "val2"
},
"condition": "context.getMethod() in ['GET', 'HEAD', 'POST']"
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
route_2
-------

- Path: /name/add
- Path Regex: #PATH_REGEX#
- Host: localhost
- Host Regex: #HOST_REGEX#
- Scheme: http|https
- Method: PUT|POST
- Class: Symfony\Bundle\FrameworkBundle\Tests\Console\Descriptor\RouteStub
- Defaults: NONE
- Requirements: NO CUSTOM
- Options:
- `compiler_class`: Symfony\Component\Routing\RouteCompiler
- `opt1`: val1
- `opt2`: val2
- Condition: context.getMethod() in ['GET', 'HEAD', 'POST']

Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
--------- ---------- ------------ ----------- -----------
 Name   Method   Scheme   Host   Path 
--------- ---------- ------------ ----------- -----------
route_2 PUT|POST http|https localhost /name/add
--------- ---------- ------------ ----------- -----------

Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
<?xml version="1.0" encoding="UTF-8"?>
<routes>
<route name="route_2" class="Symfony\Bundle\FrameworkBundle\Tests\Console\Descriptor\RouteStub">
<path regex="#PATH_REGEX#">/name/add</path>
<host regex="#HOST_REGEX#">localhost</host>
<scheme>http</scheme>
<scheme>https</scheme>
<method>PUT</method>
<method>POST</method>
<options>
<option key="compiler_class">Symfony\Component\Routing\RouteCompiler</option>
<option key="opt1">val1</option>
<option key="opt2">val2</option>
</options>
<condition>context.getMethod() in ['GET', 'HEAD', 'POST']</condition>
</route>
</routes>
Loading
Morty Proxy This is a proxified and sanitized view of the page, visit original site.