Why does Spring automatically choose the superclass types during autowiring?
For instance, if I have
@Component
public class Foo {}
@Component
public class Bar extends Foo {}
and someone autowires
@Autowired
private Foo foo;
How come Spring always chooses the supertype Foo
? Shouldn't this be an "ambiguous" mapping (and cause Spring to throw an error)?
Don't you technically have two Foo
candidates? (e.g., Bar gets automatically picked when @Component is removed from Foo...)
That might be because the autowiring is done by name, not type. If I setup my bean using xml like this:
<bean id="foo1" class="Foo"/>
<bean id="foo2" class="Bar"/>
And attempt to autowire by type:
@Autowired private Foo aFoo;
I get
org.springframework.beans.factory.NoSuchBeanDefinitionException: No unique bean of type [Foo]
Autowiring can work using both type and bean name, depending on how you have it configured.
In this case, since there are two beans of type Foo
, the Foo
instance may be chosen because it matches the name of the variable foo
.
What happens if you rename foo
to something else?
If there are two beans of same type , then spring tries to resolve dependence by the name of the variable you have specified. If the name does not match with any of the bean names, then it will throw an error. But, if it finds a bean name matching to that of variable name you specified, it will inject that bean.
So, while injecting dependencies, spring considers both , the type and the name.