Close

Spring - Beans Auto-Wiring

[Updated: Feb 3, 2017, Created: Dec 3, 2015]

Spring container can autowire dependencies implicitly. We can specify a mode of autowiring (other than the default one) using @Bean annotation.

 @Configuration
 public class Config{
    @Bean(autowire == <xyz>)
     public ABean aBean(){
        return new ABean();
    }
   .....
 }

In above code snippet, we are specifying a autowiring mode xyz, which Spring will be apply to the ABean class while injecting other beans in the same class.


The valid values of autowiring modes are: Autowire.NO, Autowire.BY_NAME and Autowire.BY_TYPE




Autowire.NO

This is the default. We have to explicitly use @Autowired at injection point. That means Spring doesn't do automatic wiring in this mode. We have to tell Spring that at what points bean wiring should happen by specifying @Autowired annotation at those points.

On finding @Autowired annotation Spring attempts to match injection point type with other registered beans type for a successful injection.




There shouldn't be any conflict (ambiguity), which means there should be no more than one bean instance of the same type registered for a given injection point, otherwise we will have NoUniqueBeanDefinitionException.



To avoid exception, we have to use @Qualifier.



Autowire.BY_TYPE

In this autowiring mode, Spring walks through type of each 'property' (the standard Java Bean property) of a given bean to match other registered beans type. If there's a match then the dependency injection happens. So basically this mode is entirely based on matching types.

In this mode, We don't need @Autowired at the injection point as Spring doesn't search for places which are annotated with @Autowired.

In this mode of autowiring, the field injection doesn't work. There must be a setter. Spring scans all setters of a bean and if the type of property matches and there is no ambiguity then injects the target property.



In case of ambiguity, we have to use @Qualifier at both places.

Autowire.BY_NAME

In this mode, beans are matched by names. Names are nothing but the identifier of the beans.

We have to use @Autowired at the injection point in this mode.

In the following example, even though there are two beans of same type, there will still be a valid match for the injection point field Service serviceBean1; That's because by default, the beans are registered as the 'method name' annotated with @Bean unless we use the 'name' element of @Bean.




We can also specify an explicit bean name using 'name' element of the @Bean




We can use setter based or constructor based autowiring as well, still the filed name (bean property) has to match.


We would typically want to use this mode of wiring, if there are multiple beans of same type which likely to cause NoUniqueBeanDefinitionException (for both Autowire.NO and Autowire.BY_TYPE modes). Using bean's name (the identifier) is a way to resolve ambiguity.

We can also use @Qualifier instead of matching by 'name'. There, we have to use the same qualifier at the injection point. In that case using the mode Autowire.By_NAME won't be significant any more because we will be matching by a qualifier not by name.



Note that in Autowire.NO mode too (in fact, in all autowiring modes), Spring framework first tries to match by type then by name. In example project below, please see AutowireNoExample2 on that.



Example project

Dependencies and Technologies Used:

  • Spring Context 4.2.3.RELEASE: Spring Context.
  • JDK 1.8
  • Maven 3.0.4

Auto Wiring Examples Select All Download
  • spring-auto-wiring
    • src
      • main
        • java
          • com
            • logicbig
              • example

See Also