Skip to content

Commit bf849ef

Browse files
committed
bug symfony#16467 Fixing bad type-hint auto-wiring bug (weaverryan)
This PR was squashed before being merged into the 2.8 branch (closes symfony#16467). Discussion ---------- Fixing bad type-hint auto-wiring bug | Q | A | ------------- | --- | Bug fix? | yes | New feature? | no | BC breaks? | no | Deprecations? | no | Tests pass? | yes | Fixed tickets | n/a | License | MIT | Doc PR | n/a Previously, if you type-hinted a bad class name, we did not set the argument value. In fact, with `continue`, we skipped setting the argument, which meant that if argument 2 was skipped, then argument 3 would be put into argument 2's location. But really, if I type-hint a non-existent class, this should throw a clear exception. afaik, in the original PR, it was said that we cannot throw an exception for a non-existent class because a later compiler-pass may manipulate those class names and "fix" them to be real classes. But, that's an edge case, and I think if you're using advanced functionality like that, you should not use auto-wiring. Throwing an exception is much more user-friendly. I personally hit this issue and was trying to figure out what was going wrong :). About the exception message: I would like to tell the user which class is type-hinted correctly, but getting the type-hinted class for a non-existent class is not possible with reflection. Thanks! cc @dunglas Commits ------- b7b182e Fixing bad type-hint auto-wiring bug
2 parents 3443230 + b7b182e commit bf849ef

File tree

2 files changed

+23
-1
lines changed

2 files changed

+23
-1
lines changed

src/Symfony/Component/DependencyInjection/Compiler/AutowirePass.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -104,7 +104,7 @@ private function completeDefinition($id, Definition $definition)
104104
// Typehint against a non-existing class
105105

106106
if (!$parameter->isDefaultValueAvailable()) {
107-
continue;
107+
throw new RuntimeException(sprintf('Cannot autowire argument %s for %s because the type-hinted class does not exist (%s).', $index + 1, $definition->getClass(), $reflectionException->getMessage()), 0, $reflectionException);
108108
}
109109

110110
$value = $parameter->getDefaultValue();

src/Symfony/Component/DependencyInjection/Tests/Compiler/AutowirePassTest.php

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -201,6 +201,21 @@ public function testDontTriggeruAutowiring()
201201

202202
$this->assertCount(0, $container->getDefinition('bar')->getArguments());
203203
}
204+
205+
/**
206+
* @expectedException \Symfony\Component\DependencyInjection\Exception\RuntimeException
207+
* @expectedExceptionMessage Cannot autowire argument 2 for Symfony\Component\DependencyInjection\Tests\Compiler\BadTypeHintedArgument because the type-hinted class does not exist (Class Symfony\Component\DependencyInjection\Tests\Compiler\NotARealClass does not exist).
208+
*/
209+
public function testClassNotFoundThrowsException()
210+
{
211+
$container = new ContainerBuilder();
212+
213+
$aDefinition = $container->register('a', __NAMESPACE__.'\BadTypeHintedArgument');
214+
$aDefinition->setAutowired(true);
215+
216+
$pass = new AutowirePass();
217+
$pass->process($container);
218+
}
204219
}
205220

206221
class Foo
@@ -298,3 +313,10 @@ public function __construct(CollisionInterface $c = null, A $a, Foo $f = null)
298313
{
299314
}
300315
}
316+
317+
class BadTypeHintedArgument
318+
{
319+
public function __construct(Dunglas $k, NotARealClass $r)
320+
{
321+
}
322+
}

0 commit comments

Comments
 (0)