1. 程式人生 > >使用Autowired和Qualifier解決多個相同型別的bean如何共存的問題

使用Autowired和Qualifier解決多個相同型別的bean如何共存的問題

@Autowired是根據型別進行自動裝配的。如果當spring上下文中存在不止一個A型別的bean時,就會丟擲BeanCreationException異常;如果Spring上下文中不存在A型別的bean,而且我們又使用A型別,也會丟擲BeanCreationException異常。

針對存在多個A型別的Bean,我們可以聯合使用@Qualifier和@Autowired來解決這些問題。
英文文件在這裡

例如

Caused by: org.springframework.beans.factory.NoUniqueBeanDefinitionException: No qualifying bean of
type 'com.yq.demo.service.UserService' available: expected single matching bean but found 2: myUserServiceImpl,userServiceImpl at org.springframework.beans.factory.config.DependencyDescriptor.resolveNotUnique(DependencyDescriptor.java:173) at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1116
) at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1066)

我們的service介面是

public interface UserService {
    public long userCount();

    public String showSpecificClassName();

    public List<User> getAllUser
(); public User addUser(User user); public void delUser(Integer id); public User updateUser(User user); public User getUserByName(String username); public User getUserByID(Integer id); }

我們有兩個實現類,分別是MyUserServiceImpl和UserServiceImpl

@Service
public class UserServiceImpl implements UserService {
    @Autowired
    private UserJpaRepository userJpaRepo;

    private static final Logger log = LoggerFactory.getLogger(UserServiceImpl.class);
    @Override
    public long userCount(){
        return userJpaRepo.count();
    }

    @Override
    public String showSpecificClassName() {
        String clsName = this.getClass().getCanonicalName();
        log.info("impl class is " + clsName);
        return clsName;
    }
    ...
@Service
public class MyUserServiceImpl implements UserService {
    @Autowired
    private UserJpaRepository userJpaRepo;

    private static final Logger log = LoggerFactory.getLogger(MyUserServiceImpl.class);
    @Override
    public long userCount(){
        return userJpaRepo.count();
    }

    @Override
    public String showSpecificClassName() {
        String clsName = this.getClass().getCanonicalName();
        log.info("impl class is " + clsName);
        return clsName;
    }

然後我們在其他地方,如controller中這樣寫

@Controller   
@RequestMapping(path="/user") 
public class UserController {
    @Autowired
    private UserService userService;

    @GetMapping(value = "/testAutowired", produces = "application/json;charset=UTF-8")
    public @ResponseBody String testAutowired (@RequestParam String name) {
        String name1 = userService.showSpecificClassName();
        return name1;
    }

當我們啟動程式時就會報錯,因為有兩個UserService的實現類。程式不知道該選擇那個。 這時可以使用Qualifier 來解決唯一性問題

    @Autowired
    @Qualifier("userServiceImpl")
    private UserService userService;

具體程式碼在這裡,歡迎加星和fork。