用实例证明@Autowired和@Resource注解先通过Type还是Name注入

Posted big-feiyang

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了用实例证明@Autowired和@Resource注解先通过Type还是Name注入相关的知识,希望对你有一定的参考价值。

注:本文中所有的“@Autowired和@Resource注入的先手顺序”一词都是指两个注解类是先通过Type注入还是先通过Name注入,并非是指两个注解在spring中执行的先后顺序

最近听子路老师讲课,课上讲解关于@Autowired和@Resource是先通过type还是先通过name注入属性的知识有点心得。

子路老师从源码的角度给大家讲了两个注解的先后顺序,但是如何通过应用的层面来进行验证呢?经过一番思考,想到了一种情况可以证明,分享给大家

1、创建一个FeiyangConfig配置类,添加扫描注解

@Configuration
@ComponentScan("com.feiyang")
public class FeiyangConfig {
}

2、创建一个Zilu类和Feiyang类并交给spring容器管理

@Component
public class Zilu {
}
@Component
public class Feiyang {
}

3、创建一个Luban类,为该类添加Zilu feiyang和Feiyang zilu属性并添加@Autowired注解,提供一个打印两个属性的方法@Component

 

@Component
public class Luban {

    @Autowired
    private Feiyang zilu;

    @Autowired
    private Zilu feiyang;

    public void print() {
        System.out.println("Feiyang zilu = " + zilu);
        System.out.println("Zilu feiyang = " + feiyang);
    }

}

 

4、新建一个测试类,初始化spring容器,获取Luban bean,调用打印方法

public class Test {

    public static void main(String[] args) {
        ApplicationContext ac = new AnnotationConfigApplicationContext(FeiyangConfig.class);
        ac.getBean(Luban.class).print();
    }

}

5、运行代码,可以看到控制台打印信息

Feiyang zilu = com.feiyang.model.Feiyang@69a10787
Zilu feiyang = com.feiyang.model.Zilu@2d127a61

得出结论:@Autowired是先通过Type注入,后通过Name注入的。因为如果是先通过Name注入,那么Feiyang zilu注入的就应该是Zilu bean,而Zilu bean注入给Feiyang类型的属性必定会报错,所以不可能是先通过Name注入,只能是先通过Type注入的。
6、将两个属性的@Autowired注解修改为@Resource注解

@Component
public class Luban {

    @Resource
    private Feiyang zilu;

    @Resource
    private Zilu feiyang;

    public void print() {
        System.out.println("Feiyang zilu = " + zilu);
        System.out.println("Zilu feiyang = " + feiyang);
    }

}

由于@Resource是先通过Name注入的,所以初始化spring的时候一定会报错。为了验证结果,我们重复一遍4的步骤,控制台打印信息如下

org.springframework.beans.factory.BeanCreationException: Error creating bean with name ‘luban‘: Injection of resource dependencies failed; nested exception is org.springframework.beans.factory.BeanNotOfRequiredTypeException: Bean named ‘zilu‘ is expected to be of type ‘com.feiyang.model.Feiyang‘ but was actually of type ‘com.feiyang.model.Zilu‘
Error creating bean with name ‘luban‘: Injection of resource dependencies failed; nested exception is org.springframework.beans.factory.BeanNotOfRequiredTypeException: Bean named ‘zilu‘ is expected to be of type ‘com.feiyang.model.Feiyang‘ but was actually of type ‘com.feiyang.model.Zilu‘

这个报错信息的意思是创建Luban这个bean的时候失败,失败原因是注入名称为zilu的bean的时候应该是注入一个Feiyang类型的bean,但是获取到的却是Zilu类型的bean,这就说明@Resource是先通过Name注入的

总结:@Autowired和@Resource注入的先后顺序的结果大家都是知道的,本次只是通过应用的层面来侧面证明一下,以后有机会可以从源码角度和大家分享一下它们注入的先后顺序

以上是关于用实例证明@Autowired和@Resource注解先通过Type还是Name注入的主要内容,如果未能解决你的问题,请参考以下文章

对于 Spring @Autowired 或者 @Resource注解为null的问题

@Autowired @Resource @Qualifier的区别

@Autowired和@Resource的区别和联系

bean基于Annotation装配;@Resource和@Autowired区别

Spring DI注解(@Autowired @Resource @Qualifier的区别)

@Autowired和@Resource到底什么区别,你明白了吗?