7.6 Spring提供的Java配置管理
7.6 Spring提供的Java配置管理
Spring
为不喜欢XML
的人提供了一种选择:如果不喜欢使用XML
来管理Bean
,以及Bean
之间的依赖关系, Spring
允许开发者使用Java
类进行配置管理。
假如有如下Person
接口的实现类。
1 | package org.crazyit.app.service.impl; |
上面的Chinese
类需要注入两个属性:name
和axe
,本示例当然也为Axe
提供了两个实现类StoneAxe
和SteelAxe
。如果采用XML
配置,相应的配置文件如下。
1 |
|
如果开发者不喜欢使用XML
配置文件, Spring
允许开发者使用Java
类进行配置上面的XML
配置文件可以替换为如下的Java
配置类。
1 | package org.crazyit.app.config; |
上面的配置文件中使用了Java
配置类的三个常用注解。
注解 | 描述 |
---|---|
@Configuration |
用于修饰一个Java 配置类 。 |
@Bean |
用于修饰一个方法 ,将该方法的返回值定义成容器中的一个Bean 。 |
@Value |
用于修饰一个Field ,用于为该Field 配置一个值,相当于配置一个变量。 |
一旦使用了Java
配置类来管理Spring
容器中的Bean
及其依赖关系,此时就需要使用如下方式来创建Spring
容器:
1 | ApplicationContext ctx = new |
上面的AnnotationConfigApplicationContext
类会根据**Java
配置类**来创建Spring
容器。不仅如此,该类还提供了一个register(Class)
方法用于添加Java
配置类。
使用Java
配置类时,还有如下常用的注解。
注解 | 描述 |
---|---|
@Import |
修饰一个Java 配置类 ,用于向当前Java 配置类中导入其他Java 配置类。 |
@Scope |
用于修饰一个方法 ,指定该方法对应的Bean 的生命域。 |
@Lazy |
用于修饰一个方法 ,指定该方法对应的Bean 是否需要延迟初始化。 |
@DependsOn |
用于修饰一个方法 ,指定在初始化该方法对应的Bean 之前初始化所依赖的Bean 。 |
使用XML配置文件管理Bean和使用配置类管理Bean的对比
就普通用户习惯来看,还是使用XML
配置文件管理Bean
及其依赖关系更为方便,毕竟使用XML
文件来管理Bean
及其依赖关系是为了解耦。但这种Java
配置类的方式又退回到Java
代码耦合层次,只是将这种耦合集中到一个或多个Java
配置类中。
为什么引入配置类来管理Bean
实际上, Spring
提供@Configuration
和@Bean
并不是为了完全取代XML
配置,只是希望将它作为XML
配置的一种补充。对于Spring
框架的用户来说, Spring
配置文件的”急剧膨胀”是一个让人头痛的点,因此Spring
框架从2.0
版本开始就不断地寻找各种对配置文件”减肥”的方法。
后面所介绍的各种注解也都是为了简化Spring
配置文件而出现的,但由于注解引入时间较晚,因此在一些特殊功能的支持上,注解还不如XML
强大。
使用XML还是使用注解
因此,在目前的多数项目中,
- 要么**完全使用
XML
**配置方式管理Bean
的配置, - 要么使用以注解为主、
XML
为辅的配置方式管理Bean
的配置,想要完全放弃XML
配置还是比较难的。
为什么会混用XML和注解
之所以会出现两者共存的情况,主要归结为三个原因:
- 其一,目前绝大多数采用
Spring
进行开发的项目,几乎都是基于XML
配置方式的,Spring
在引入注解的同时,必须保证注解能够与XML
和谐共存,这是前提; - 其二,由于注解引入较晚,因此功能也没有发展多年的
XML
强大,对于复杂的配置,注解还很难独当一面,在一段时间内仍然需要XML
的配合才能解决问题; - 其三,
Spring
的Bean
的配置方式与Spring
核心模块之间是解耦的,因此,改变配置方式对Spring
的框架自身是透明的。Spring
可以通过使用Bean
后处理器(BeanPostProcessor)
非常方便地增加对于注解的支持。以XML配置为主还是以Java类配置为主
因此,在实际项目中可能会混合使用XML
配置和Java
类配置,在这种混合下存在一个问题:项目到底以XML
配置为主,还是以Java
类配置为主呢?以XML配置为主时
如果以XML
配置为主,就需要让XML
配置能加载Java
类配置。这并不难,只要在XML
配置中增加如下代码即可:由于以1
2
3
4
5
<beans ....>
....
<bean class="org.crazyit.app.config.AppConfig"/>
</beans>XML
配置为主,因此应用创建Spring
容器时,还是以这份XML
配置文件为参数来创建ApplicationContext
对象。那么Spring
会先加载这份XML
配置文件,再根据这份XML
配置文件的指示去加载指定的Java
配置类。如果以Java类配置为主
如果以Java
类配置为主,就需要让Java
配置类能加载XML
配置。这就需要借助于@)ImportResource
注解,这个注解可修饰Java
配置类,用于导入指定的XML
配置文件。也就是在Java
配置类上增加如下注解:由于以1
2
3
4
5
6
7
// 导入XML配置
public class AppConfig
{
......
}Java
类配置为主,因此应用创建Spring
容器时,应以Java
配置类为参数,通过创建AnnotationConfigApplicationContext
对象作为Spring
容器。那么Spring
会先加载这个Java
配置类,再根据这个Java
配置类的指示去加载指定的XML
配置文件。