diff --git a/src/Symfony/Bundle/DependencyInjection/Configuration.php b/src/Symfony/Bundle/DependencyInjection/Configuration.php index cc7326d2e6..44f08739e5 100644 --- a/src/Symfony/Bundle/DependencyInjection/Configuration.php +++ b/src/Symfony/Bundle/DependencyInjection/Configuration.php @@ -663,6 +663,17 @@ private function addDefaultsSection(ArrayNodeDefinition $rootNode): void } return $normalizedDefaults; + }) + ->end() + ->validate() + ->always(static function (array $defaults): array { + foreach (['mcp', 'graph_ql_operations', 'state_options', 'links', 'openapi'] as $option) { + if (null !== ($defaults[$option] ?? null) && ('openapi' !== $option || !\is_bool($defaults[$option]))) { + throw new InvalidConfigurationException(\sprintf('The "defaults.%s" option is not supported, it needs objects. Set it on the resources instead.', $option)); + } + } + + return $defaults; }); $this->defineDefault($defaultsNode, new \ReflectionClass(ApiResource::class), $nameConverter); diff --git a/tests/Symfony/Bundle/DependencyInjection/ConfigurationTest.php b/tests/Symfony/Bundle/DependencyInjection/ConfigurationTest.php index 24c952b015..ee90abfd62 100644 --- a/tests/Symfony/Bundle/DependencyInjection/ConfigurationTest.php +++ b/tests/Symfony/Bundle/DependencyInjection/ConfigurationTest.php @@ -277,6 +277,39 @@ public function testExceptionToStatusConfigWithInvalidHttpStatusCode($invalidHtt ]); } + public static function objectDefaultProvider(): iterable + { + yield 'mcp' => ['mcp', ['tool' => ['description' => 'Get a book']]]; + yield 'graph_ql_operations' => ['graph_ql_operations', [['class' => 'ApiPlatform\Metadata\GraphQl\Query']]]; + yield 'state_options' => ['state_options', ['entity_class' => 'App\Entity\Book']]; + yield 'links' => ['links', [['rel' => 'preload', 'href' => '/books']]]; + yield 'openapi' => ['openapi', ['summary' => 'A book']]; + } + + #[DataProvider('objectDefaultProvider')] + public function testDefaultsThatNeedObjects(string $key, array $value): void + { + $this->expectException(InvalidConfigurationException::class); + $this->expectExceptionMessage(\sprintf('The "defaults.%s" option is not supported, it needs objects. Set it on the resources instead.', $key)); + + $this->processor->processConfiguration($this->configuration, [ + 'api_platform' => [ + 'defaults' => [$key => $value], + ], + ]); + } + + public function testOpenapiDefaultCanBeABoolean(): void + { + $config = $this->processor->processConfiguration($this->configuration, [ + 'api_platform' => [ + 'defaults' => ['openapi' => false], + ], + ]); + + $this->assertFalse($config['defaults']['openapi']); + } + public static function invalidHttpStatusCodeValueProvider(): array { return [