Wednesday, January 29, 2014

Spring beans autowiring concepts

In spring framework, setting bean dependencies in configuration files is a good practice to follow, but the spring container is also able to autowire relationships between collaborating beans. This means that it is possible to automatically let Spring resolve collaborators (other beans) for your bean by inspecting the contents of the BeanFactory.Autowiring is specified per bean and can thus be enabled for some beans, while other beans will not be autowired.
Spring autowiring modes
Spring autowiring modes

The autowiring functionality has five modes. These are ‘no’, ‘byName’, ‘byType’, ‘constructor’, and ‘autodetect’. The default mode is “no” i.e. by default autowiring is turned off.
Sections in this post:

Various autowiring modes used in bean configuration file
Using autowiring with @Autowired annotations
Using @Qualifier in case of conflict
Making autowiring error safe using required=false
Excluding a bean from being available for autowiring

Various autowiring modes used in bean configuration file

As shown in picture above, there are five auto wiring modes. Lets discuss them one by one.
  • no: This option is default for spring framework and it means that autowiring is OFF. You have to explicitly set the dependencies using tags in bean definitions.
  • byName: This option enables the dependency injection based on bean names. When autowiring a property in bean, property name is used for searching a matching bean definition in configuration file. If such bean is found, it is injected in property. If no such bean is found, a error is raised.
  • byType: This option enables the dependency injection based on bean types. When autowiring a property in bean, property’s class type is used for searching a matching bean definition in configuration file. If such bean is found, it is injected in property. If no such bean is found, a error is raised.
  • constructor: Autowiring by constructor is similar to byType, but applies to constructor arguments. In autowire enabled bean, it will look for class type of constructor arguments, and then do a autowire by type on all constructor arguments. Please note that if there isn’t exactly one bean of the constructor argument type in the container, a fatal error is raised.
  • autodetect: Autowiring by autodetect uses either of two modes i.e. constructor or byType modes. First it will try to look for valid constructor with arguments, If found the constructor mode is chosen. If there is no constructor defined in bean, or explicit default no-args constructor is present, the autowire byType mode is chosen.

Using autowiring with @Autowired annotations

Apart from the autowiring modes provided in bean configuration file, autowiring can be specified in bean classes also using @Autowired annotation. To use @Autowired annotation in bean classes, you must first enable the annotation in spring application using below configuration.
Same can be acheived using ‘AutowiredAnnotationBeanPostProcessor’ bean definition in configuration file.
Now, when annotation configuration has been enables, you are free to autowire bean dependencies using @Autowired, the way you like. This is done by three ways:
1) @Autowired on properties
When @Autowired is used on properties, it is equivalent to autowiring by ‘byType’ in configuration file.
?
1
2
3
4
5
6
7
8
9
10
11
12
13
public class EmployeeBean
{
    @Autowired
    private DepartmentBean departmentBean;
      
    public DepartmentBean getDepartmentBean() {
        return departmentBean;
    }
    public void setDepartmentBean(DepartmentBean departmentBean) {
        this.departmentBean = departmentBean;
    }
    //More code
}
2) @Autowired on property setters
When @Autowired is used on setters, it is also equivalent to autowiring by ‘byType’ in configuration file.
?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
public class EmployeeBean
{
    private DepartmentBean departmentBean;
      
    public DepartmentBean getDepartmentBean() {
        return departmentBean;
    }
     
    @Autowired
    public void setDepartmentBean(DepartmentBean departmentBean) {
        this.departmentBean = departmentBean;
    }
    //More code
}
3) @Autowired on constructors
When @Autowired is used on bean’s constructor, it is also equivalent to autowiring by ‘constructor’ in configuration file.
?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
package com.howtodoinjava.autowire.constructor;
  
public class EmployeeBean
{
    @Autowired
    public EmployeeBean(DepartmentBean departmentBean)
    {
        this.departmentBean = departmentBean;
    }
     
    private DepartmentBean departmentBean;
  
    public DepartmentBean getDepartmentBean() {
        return departmentBean;
    }
    public void setDepartmentBean(DepartmentBean departmentBean) {
        this.departmentBean = departmentBean;
    }
    //More code
}

Using @Qualifier in case of conflict

As we learned that if we are using autowiring in ‘byType’ mode and dependencies are looked for property class types. If no such type is found, an error is thrown. But, what if there are two or more beans for same class type.
In this case spring will not be able to choose correct bean to inject into property, and you will need to help the container using qualifiers.
To resolve a specific bean using qualifier, we need to use @Qualifier annotation along with @Autowired annotation and pass the bean name in annotation parameter. Take a look below for example:
?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
public class EmployeeBean
{
    @Autowired
    @Qualifier("finance")
    private DepartmentBean departmentBean;
      
    public DepartmentBean getDepartmentBean() {
        return departmentBean;
    }
    public void setDepartmentBean(DepartmentBean departmentBean) {
        this.departmentBean = departmentBean;
    }
    //More code
}
where duplicate beans are as below:
?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
xml version="1.0" encoding="UTF-8"?>
<beans>
    <context:annotation-config />
      
    <bean id="employee" class="com.howtodoinjava.autowire.constructor.EmployeeBean" autowire="constructor">
        <property name="fullName" value="Lokesh Gupta"/>
    </bean>
    
    <bean id="humanResource" class="com.howtodoinjava.autowire.constructor.DepartmentBean" >
        <property name="name" value="Human Resource" />
    </bean>
     
    
     <bean id="finance"      class="com.howtodoinjava.autowire.constructor.DepartmentBean" >
        <property name="name" value="Finance" />
    </bean>
</beans>

Making autowiring error safe using required=false

Even if you have used utmost care in autowiring bean dependencies, still you may find strange lookup failures. So, solve this issue, you will need to make autowiring optional so that if no dependency is found, application should not throw any exception and autowiring should simpy be ignored.
This can be done in two ways:
1)If you want to make specific bean autowiring non-mandatory for a specific bean property, use required=”false” attribute in @Autowired annoration
?
1
2
3
@Autowired (required=false)
@Qualifier ("finance")
private DepartmentBean departmentBean;
2) If you want to apply optional autowiring at global level i.e. for all properties in all beans; use below configuration setting.
?
1
2
3
<bean class="org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor">
    <property name="requiredParameterValue" value="false" />
</bean>

Excluding a bean from being available for autowiring

By default, autowiring scan and matches all bean definitions in scope. If you want to exclude some bean definitions so that they can not be injected through autowiring mode, you can do this using ‘autowire-candidate’ set to false.
1) Using ‘autowire-candidate‘ as false totally exclude a bean from being an autowire candidate. It totally exclude that specific bean definition from being available to the autowiring infrastructure.
?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
xml version="1.0" encoding="UTF-8"?>
<beans>
    <context:annotation-config />
      
    <bean id="employee" class="com.howtodoinjava.autowire.constructor.EmployeeBean" autowire="constructor">
        <property name="fullName" value="Lokesh Gupta"/>
    </bean>
    
    <bean id="humanResource" class="com.howtodoinjava.autowire.constructor.DepartmentBean" >
        <property name="name" value="Human Resource" />
    </bean>
     
    
     <bean id="finance"      class="com.howtodoinjava.autowire.constructor.DepartmentBean" autowire-candidate="false">
        <property name="name" value="Finance" />
    </bean>
</beans>
2) Another option is to limit autowire candidates based on pattern-matching against bean names. The top-level element accepts one or more patterns within its ‘default-autowire-candidates‘ attribute. For example, to limit autowire candidate status to any bean whose name ends with ‘Impl’, provide a value of ‘*Impl’. To provide multiple patterns, define them in a comma-separated list.
?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
xml version="1.0" encoding="UTF-8"?>
<beans default-autowire-candidates="*Impl,*Dao">
    <context:annotation-config />
      
    <bean id="employee" class="com.howtodoinjava.autowire.constructor.EmployeeBean" autowire="constructor">
        <property name="fullName" value="Lokesh Gupta"/>
    </bean>
    
    <bean id="humanResource" class="com.howtodoinjava.autowire.constructor.DepartmentBean" >
        <property name="name" value="Human Resource" />
    </bean>
     
    
     <bean id="finance"      class="com.howtodoinjava.autowire.constructor.DepartmentBean" autowire-candidate="false">
        <property name="name" value="Finance" />
    </bean>
</beans>
Note that an explicit value of ‘true’ or ‘false’ for a bean definition’s ‘autowire-candidate’ attribute always takes precedence, and for such beans, the pattern matching rules will not apply.
That’s all about autowiring feature available in spring framework. If you have any doubt, please drop a comment.
Sourcecode Download
Happy Learning !!

4 comments:

oakleyses said...

louis vuitton handbags, oakley sunglasses, louboutin, longchamp outlet, nike shoes, louis vuitton outlet stores, chanel handbags, burberry outlet, prada outlet, jordan shoes, tiffany and co, michael kors outlet, tory burch outlet, louis vuitton outlet, longchamp handbags, nike free, true religion jeans, michael kors outlet, kate spade outlet, polo ralph lauren outlet, tiffany and co, prada handbags, polo ralph lauren outlet, michael kors outlet, michael kors outlet, longchamp handbags, oakley sunglasses, ray ban sunglasses, kate spade handbags, burberry outlet, louis vuitton outlet, louboutin outlet, louboutin, coach factory outlet, air max, air max, coach outlet, gucci outlet, christian louboutin shoes, michael kors outlet, coach purses, ray ban sunglasses, michael kors outlet, louis vuitton, coach outlet store online, true religion jeans, oakley sunglasses cheap

oakleyses said...

ralph lauren, lululemon, air max, hollister, north face, nike air max, polo lacoste, vanessa bruno, timberland, vans pas cher, louboutin, louis vuitton, oakley pas cher, air max pas cher, nike roshe run, air max, true religion outlet, barbour, sac longchamp, air force, hollister, sac louis vuitton, nike free, polo ralph lauren, nike trainers, louis vuitton uk, nike roshe, sac hermes, longchamp, michael kors, sac burberry, sac guess, mulberry, new balance pas cher, converse pas cher, sac louis vuitton, hogan outlet, nike tn, north face, true religion outlet, ray ban pas cher, michael kors, air jordan, nike blazer, nike free pas cher, michael kors pas cher, abercrombie and fitch, ray ban sunglasses

oakleyses said...

mac cosmetics, mont blanc, marc jacobs, canada goose outlet, nike huarache, vans shoes, soccer jerseys, hollister, giuseppe zanotti, beats by dre, abercrombie and fitch, longchamp, insanity workout, celine handbags, bottega veneta, ghd, nfl jerseys, north face outlet, chi flat iron, ugg boots, birkin bag, ugg australia, canada goose, herve leger, ugg pas cher, rolex watches, valentino shoes, canada goose uk, canada goose, ferragamo shoes, canada goose, ugg boots, uggs outlet, north face jackets, soccer shoes, asics running shoes, new balance shoes, p90x, lululemon outlet, canada goose jackets, mcm handbags, instyler, babyliss pro, ugg, wedding dresses, jimmy choo outlet, reebok outlet, nike roshe run

oakleyses said...

parajumpers, karen millen, air max, converse, pandora charms, moncler, louboutin, moncler, links of london, lancel, juicy couture outlet, oakley, hollister, pandora charms, supra shoes, thomas sabo, canada goose, gucci, wedding dresses, timberland boots, swarovski crystal, air max, coach outlet store online, moncler, ray ban, canada goose, moncler, ugg, louis vuitton, swarovski, hollister, montre homme, moncler, hollister clothing store, ralph lauren, rolex watches, moncler outlet, moncler, iphone 6 cases, baseball bats, juicy couture outlet, toms shoes, vans, pandora jewelry, ugg, converse shoes