【发布时间】:2014-06-12 08:34:04
【问题描述】:
我正在将一些基于 Xml 的 spring 配置转移到基于 Java 的过程中。
以前,我有意识地将 Xml <bean class='foo' /> 声明与 @Component 映射根据具体情况混合在一起,作为记录不明显 bean 的一种方法。
一个典型的用例是,如果我声明将修改 spring 本身行为的 bean,我将显式声明它们,而不是让它们被发现,纯粹是为了提高配置文件的清晰度。
但是,这些 bean 通常需要@Autowiring 的度数。如果我在 Java 配置中自己 new bean,我将负责执行此连接 - 这是没有意义的。
是否有一个纯 Java 配置选项可以显式地向 Spring 提供一个类,并让它管理实例化?
即:
给定班级:
public class MyFunkySpringBean implements InitializingBean {
@Autowired Foo foo;
}
在 XML 配置中,这将被简单地声明为:
<bean class="MyFunkySpringBean" />
在 Java 语法中是否有等价物,我可以将 bean 类显式声明给 Spring,但不负责提供实际实例 - 将其留给 Spring。
例如:
@Configuration
public class MyAppConfig {
// Explictly provide the class, not the instance to Spring
@Bean
public MyFunkySpringBean funkyBean; // No instance -- it's up to Spring to build
}
明确地说,我不想必须这样做:
@Configuration
public class MyAppConfig {
@Bean
public MyFunkySpringBean funkyBean() {
MyFunkySpringBean bean = new MyFunkySpringBean();
bean.foo = new Foo();
// other dependencies go here
return bean;
}
}
这样的设施是否存在于 Spring 中?
【问题讨论】:
-
我不明白这个问题。您想提供一个类并让 Spring 为您管理其生命周期(这是常见行为),或者您想定义应如何生成该类并让 Spring 在自动装配时管理此逻辑?
-
第一个。我想要一种无 XML 的方式来提供一个类并让 Spring 管理它的生命周期。我不想对
newing 负责。但是,我不想通过@Component扫描发现它——我想明确说明这个类的声明。 -
您改写的问题仍然没有使用构造函数自动装配!我可以看到您不了解 Spring 中的属性自动装配是如何工作的……有 bean 后处理器,它检测带有
@Autowired注释的属性和方法。这些后处理器在使用 Java 配置时仍然处于活动状态。您不需要手动进行自动装配。它将在春天完成!您需要致电bean.foo = new Foo()的假设不正确...再次检查Sotirios 答案(主要是强调的陈述)。 -
更清楚一点 - bean 实例化和依赖注入(包括自动装配)是两个独立的过程......除非您使用构造函数注入。 构造函数自动装配 是目前 Java 配置中唯一无法实现的。在 Java 配置中,您负责创建实例......但是,一旦从
@Bean方法返回实例,它将进行额外处理 - 代理、自动装配、特殊接口和注释处理(工厂 bean、初始化bean,常见注释,...)。所有的春天魔法仍然存在。