diff --git a/src/Symfony/Component/DependencyInjection/Compiler/CheckExceptionOnInvalidReferenceBehaviorPass.php b/src/Symfony/Component/DependencyInjection/Compiler/CheckExceptionOnInvalidReferenceBehaviorPass.php index fd3173831d2e6..f4d01d8bceef9 100644 --- a/src/Symfony/Component/DependencyInjection/Compiler/CheckExceptionOnInvalidReferenceBehaviorPass.php +++ b/src/Symfony/Component/DependencyInjection/Compiler/CheckExceptionOnInvalidReferenceBehaviorPass.php @@ -25,9 +25,6 @@ class CheckExceptionOnInvalidReferenceBehaviorPass extends AbstractRecursivePass { private $serviceLocatorContextIds = []; - /** - * {@inheritdoc} - */ public function process(ContainerBuilder $container) { $this->serviceLocatorContextIds = []; @@ -58,15 +55,7 @@ protected function processValue($value, bool $isRoot = false) if (isset($this->serviceLocatorContextIds[$currentId])) { $currentId = $this->serviceLocatorContextIds[$currentId]; $locator = $this->container->getDefinition($this->currentId)->getFactory()[0]; - - foreach ($locator->getArgument(0) as $k => $v) { - if ($v->getValues()[0] === $value) { - if ($k !== $id) { - $currentId = $k.'" in the container provided to "'.$currentId; - } - throw new ServiceNotFoundException($id, $currentId, null, $this->getAlternatives($id)); - } - } + $this->throwServiceNotFoundException($value, $currentId, $locator->getArgument(0)); } if ('.' === $currentId[0] && $graph->hasNode($currentId)) { @@ -80,14 +69,21 @@ protected function processValue($value, bool $isRoot = false) $currentId = $sourceId; break; } + + if (isset($this->serviceLocatorContextIds[$sourceId])) { + $currentId = $this->serviceLocatorContextIds[$sourceId]; + $locator = $this->container->getDefinition($this->currentId); + $this->throwServiceNotFoundException($value, $currentId, $locator->getArgument(0)); + } } } - throw new ServiceNotFoundException($id, $currentId, null, $this->getAlternatives($id)); + $this->throwServiceNotFoundException($value, $currentId, $value); } - private function getAlternatives(string $id): array + private function throwServiceNotFoundException(Reference $ref, string $sourceId, $value): void { + $id = (string) $ref; $alternatives = []; foreach ($this->container->getServiceIds() as $knownId) { if ('' === $knownId || '.' === $knownId[0]) { @@ -100,6 +96,31 @@ private function getAlternatives(string $id): array } } - return $alternatives; + $pass = new class() extends AbstractRecursivePass { + public $ref; + public $sourceId; + public $alternatives; + + /** + * @return mixed + */ + public function processValue($value, bool $isRoot = false) + { + if ($this->ref !== $value) { + return parent::processValue($value, $isRoot); + } + $sourceId = $this->sourceId; + if (null !== $this->currentId && $this->currentId !== (string) $value) { + $sourceId = $this->currentId.'" in the container provided to "'.$sourceId; + } + + throw new ServiceNotFoundException((string) $value, $sourceId, null, $this->alternatives); + } + }; + $pass->ref = $ref; + $pass->sourceId = $sourceId; + $pass->alternatives = $alternatives; + + $pass->processValue($value, true); } } diff --git a/src/Symfony/Component/DependencyInjection/Tests/Compiler/CheckExceptionOnInvalidReferenceBehaviorPassTest.php b/src/Symfony/Component/DependencyInjection/Tests/Compiler/CheckExceptionOnInvalidReferenceBehaviorPassTest.php index b2bd5023d8f6a..f98d06560d089 100644 --- a/src/Symfony/Component/DependencyInjection/Tests/Compiler/CheckExceptionOnInvalidReferenceBehaviorPassTest.php +++ b/src/Symfony/Component/DependencyInjection/Tests/Compiler/CheckExceptionOnInvalidReferenceBehaviorPassTest.php @@ -82,7 +82,11 @@ public function testProcessDefinitionWithBindings() $this->addToAssertionCount(1); } - public function testWithErroredServiceLocator() + /** + * @testWith [true] + * [false] + */ + public function testWithErroredServiceLocator(bool $inline) { $this->expectException(ServiceNotFoundException::class); $this->expectExceptionMessage('The service "foo" in the container provided to "bar" has a dependency on a non-existent service "baz".'); @@ -91,11 +95,17 @@ public function testWithErroredServiceLocator() ServiceLocatorTagPass::register($container, ['foo' => new Reference('baz')], 'bar'); (new AnalyzeServiceReferencesPass())->process($container); - (new InlineServiceDefinitionsPass())->process($container); + if ($inline) { + (new InlineServiceDefinitionsPass())->process($container); + } $this->process($container); } - public function testWithErroredHiddenService() + /** + * @testWith [true] + * [false] + */ + public function testWithErroredHiddenService(bool $inline) { $this->expectException(ServiceNotFoundException::class); $this->expectExceptionMessage('The service "bar" has a dependency on a non-existent service "foo".'); @@ -104,7 +114,9 @@ public function testWithErroredHiddenService() ServiceLocatorTagPass::register($container, ['foo' => new Reference('foo')], 'bar'); (new AnalyzeServiceReferencesPass())->process($container); - (new InlineServiceDefinitionsPass())->process($container); + if ($inline) { + (new InlineServiceDefinitionsPass())->process($container); + } $this->process($container); }
Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.
Alternative Proxies: