• The @Qualifier annotation is used to resolve the autowiring conflict, when there are multiple beans of same type.
  • The @Qualifier annotation can be used on any class annotated with @Component or on method annotated with @Bean .
  • This annotation can also be applied on constructor arguments or method parameters

Example1:

In Spring, @Qualifier means, which bean is qualify to autowired on a field.

See following scenario :

Autowiring Example

See below example, it will autowired a “person” bean into customer’s person property.

package com.codinko.common;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;

public class Customer {

	@Autowired
	private Person person;
	//...
}

But, two similar beans “com.codinko.common.Person” are declared in bean configuration file. Will Spring know which person bean should autowired?

<beans xmlns="http://www.springframework.org/schema/beans"
	xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
	xsi:schemaLocation="http://www.springframework.org/schema/beans
	http://www.springframework.org/schema/beans/spring-beans-2.5.xsd">

<bean 
class ="org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor"/>
	
	<bean id="customer" class="com.codinko.common.Customer" />
		
	<bean id="personA" class="com.codinko.common.Person" >
		<property name="name" value="Roy" />
	</bean>
	
	<bean id="personB" class="com.mkyong.common.Person" >
		<property name="name" value="Tommy" />
	</bean>

</beans>

When you run above example, it hits below exception :

Caused by: org.springframework.beans.factory.NoSuchBeanDefinitionException: 
	No unique bean of type [com.codinko.common.Person] is defined: 
		expected single matching bean but found 2: [personA, personB]

@Qualifier Example

To fix above problem, you need @Qualifier to tell Spring about which bean should autowired.

package com.mkyong.common;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;

public class Customer {

	@Autowired
	@Qualifier("personA")
	private Person person;
	//...
}

In this case, bean “personA” is autowired.

Customer [person=Person [name=mkyongA]]

 

Example2:

Most Spring applications only need a single transaction manager, but there may be situations where you want multiple independent transaction managers in a single application. The value attribute of the @Transactional annotation can be used to optionally specify the identity of thePlatformTransactionManager to be used. This can either be the bean name or the qualifier value of the transaction manager bean. For example, using the qualifier notation, the following Java code

  public class TransactionalService {
  
    @Transactional("order")
    public void setSomething(String name) { ... }
  
    @Transactional("account")
    public void doSomething() { ... }
  }

could be combined with the following transaction manager bean declarations in the application context.

  <tx:annotation-driven/>

  <bean id="transactionManager1" class="org.springframework.jdbc.DataSourceTransactionManager">
    ...
    <qualifier value="order"/>
  </bean>

  <bean id="transactionManager2" class="org.springframework.jdbc.DataSourceTransactionManager">
    ...
    <qualifier value="account"/>
  </bean>  

In this case, the two methods on TransactionalService will run under separate transaction managers, differentiated by the “order” and “account” qualifiers. The default <tx:annotation-driven> target bean name transactionManager will still be used if no specifically qualified PlatformTransactionManager bean is found.