Spring-依赖注入-哪个优先?

问题描述

我知道有3种使用Spring进行依赖注入的方法:字段,设置器和构造函数注入。

但是说我们在同一个组件中有更多的三个,就像这样:

import base.service.FortuneService;

@Component
public class FootballCoach implements Coach {
    
    //Field Injection
    @Autowired
    private FortuneService fortuneService;
    
    //setter Injection
    @Autowired
    public void setFortuneService(FortuneService fortuneService) {
        this.fortuneService = fortuneService;
    }
    //constructor Injection
    @Autowired
    public FootballCoach(FortuneService fortuneService) {
        this.fortuneService = fortuneService;
    }
}

哪个优先?可以这么说吗? Spring是否将全部3个都做并覆盖fortuneService字段两次?如果是这样,最后一个是哪个?还是只选择一种依赖注入?

我运行上面的代码没有问题,并且得到了以下日志,但是我真的不知道如何读取它们。

注意:FortuneService是一个接口,我有一个实现它的HappyFortuneService类。

Sep 10,2020 11:40:44 AM org.springframework.beans.factory.support.DefaultSingletonBeanRegistry getSingleton
FINE: Creating shared instance of singleton bean 'footballCoach'
Sep 10,2020 11:40:44 AM org.springframework.beans.factory.support.DefaultSingletonBeanRegistry getSingleton
FINE: Creating shared instance of singleton bean 'happyFortuneService'
Sep 10,2020 11:40:44 AM org.springframework.beans.factory.support.ConstructorResolver createArgumentArray
FINE: Autowiring by type from bean name 'footballCoach' via constructor to bean named 'happyFortuneService'
Sep 10,2020 11:40:44 AM org.springframework.beans.factory.support.DefaultSingletonBeanRegistry getSingleton
FINE: Creating shared instance of singleton bean 'tennisCoach'
Sep 10,2020 11:40:44 AM org.springframework.beans.factory.support.ConstructorResolver createArgumentArray
FINE: Autowiring by type from bean name 'tennisCoach' via constructor to bean named 'happyFortuneService'

解决方法

对于初学者来说,不要那样做。

话虽如此,以下将按顺序发生:

  1. 它将使用FortuneService实例调用构造函数,因为在任何其他事情发生之前,首先需要构造该对象。
  2. 它将使用@Autowired的实例注入用FortuneService注释的字段
  3. 它将调用带有@Autowired实例的FortuneService注释的方法

现在取决于FortuneService的范围,它将注入单例(默认值)或创建一个新实例(当bean处于原型范围内时)。

注意:可以从sourceAutowiredAnnotationBeanPostProcessor中推断出排序。调用构造函数是合乎逻辑的,但是字段与方法的顺序来自buildAutowiringMetadata方法。首先检测字段,然后检测方法。

相关问答

Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其...
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。...
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbc...