在即时期间Spring Springow?

时间:2018-03-30 17:05:09

标签: spring constructor autowired

在重构应用程序并通过Spring实现注入时,在实例化阶段获取自动对象将会很有帮助。我不能让它工作(并且会理解它是否根本不起作用;实例化将非常棘手)但是仍然想要在这里问问题以确保。 出于测试目的,我创建了这个bean:

validate

意在注入此组件:

import org.springframework.stereotype.Repository;

@Repository
public class MyService {
    private String name;

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }
}

关联的applicationContext是:

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

import de.sample.spring.service.MyService;

@Component
public class MyComponent {

    @Autowired
    private MyService myService;

    public MyComponent() {
        System.out.println("MyService during instantiation="+myService);
        showInternallyMyService();
    }

    @Autowired
    private void setMyService(MyService myService) {
        System.out.println("MyService during instantion via setter="+myService);
    }

    private void showInternallyMyService() {
        System.out.println("MyService during instantiation via constructor call="+myService);
    }

    public void showWhenExternalCalledMyService() {
        System.out.println("MyService when show has been called after instatiation="+myService);
    }   
}

这些东西然后由:

运行
<?xml version="1.0" encoding="UTF-8"?>

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

     <!-- enable autowire -->
    <context:annotation-config />
    <context:component-scan base-package="de.sample.spring.service" />
    <context:component-scan base-package="de.sample.spring.component" />

</beans>

结果日志会显示这些消息

  

实例化期间的MyService = null

     

实例化期间的MyService通过构造函数call = null

     通过setter = de.sample.spring.service.MyService@2ea227af

实例化期间的

MyService      

在instantiation :: de.sample.spring.service.MyService@2ea227af

之后调用show时的MyService

可以看出&#34; Autowired&#34; object在构造函数阶段为null,仅在运行阶段才实例化。正如已经说过的 - 我认为这是它的工作方式,但我仍然希望我错了,并且能够设法让它在构造函数中访问自动装配。我知道,我可以使用带有属性的构造函数 - 这可以解决我的问题,但我想知道是否可以使用其他方法进行管理。

3 个答案:

答案 0 :(得分:2)

Beans在构造函数执行后自动装配...默认情况下。 如果你想在施工时自动装配它,你必须在构造函数@autowire它:

    @Autowired
    public MyComponent(MyService myService) {
        System.out.println("MyService during intantiation="+myService);
        showInternallyMyService();
    }

答案 1 :(得分:1)

  • 您可以尝试@watchme提到的方式,但请注意,使用这种方式将使它成为一种不可变对象,但确保所需的依赖项不为null。
  • 同样在一个字段上使用@Autowired,你不需要一个setter方法,一旦你的bean的构造函数完成了分配/创建对象, Spring将扫描此注释,并将注入您注释的对象实例。

答案 2 :(得分:0)

这按设计工作。在初始化阶段,初始化bean并完成依赖注入。

如果要保证已注入所有依赖项,则应在初始化回调中实现逻辑。使用@PostConstruct注释:

@Component
public class MyComponent {

    @Autowired
    private MyService myService;

    public MyComponent() {
        System.out.println("MyService during intantiation="+myService);
    }

    @Autowired
    private void setMyService(MyService myService) {
        System.out.println("MyService during instantion via setter="+myService);
    }

    @PostConstruct
    private void showInternallyMyService() {
        System.out.println("MyService during initialization="+myService);
    }  
}