Spring 3.0 中的配置简化

工程 | Chris Beams | 2009 年 12 月 22 日 | ...

这是由 Keith 昨天开始的关于“Spring 3 简化”系列文章的第二篇,我想简要介绍一下 Spring 新的 @Configuration 注解和相关支持。

熟悉 Spring JavaConfig 项目的人都知道,带有 @Configuration 注解的类扮演着与 Spring XML 文件非常相似的角色。 它提供了一种以代码为中心的声明 Spring Bean 定义的方式,只需使用方法和注解即可。 你可以称它为简单的旧配置* :) 这意味着对于简单的情况,不需要任何 XML!

让我们开始吧。 为了演示 @Configuration 功能,我在新的 spring-samples SVN 存储库中创建了一个 非常简单的项目。 你可能需要同步并立即构建它。 你需要一个 Subversion 客户端和最新版本的 Maven。

svn co https://src.springframework.org/svn/spring-samples/configuration-basic/trunk configuration-basic cd configuration-basic mvn clean test [...] Tests run: 1, Failures: 0, Errors: 0, Skipped: 0

[INFO] ------------------------------------------------------------------------ [INFO] BUILD SUCCESSFUL [INFO] ------------------------------------------------------------------------

Eclipse .classpath 和 .project 元数据也包含在结账中,因此你可以使用 SpringSource Tool Suite 或安装了 m2eclipse 插件 的任何最新版本的 Eclipse 导入该项目。 在这两种情况下,都使用“文件”->“导入”->“将现有项目导入工作空间”。

首先,让我们看看 AppConfig.java。 这个带有 @Configuration 注解的类扮演着与基于 XML 的 Spring 应用程序中的 app-config.xml 相同的角色。 在查看项目时,这是一个很好的起点,因为它充当对象实例如何在运行时连接和管理的“蓝图”。


@Configuration
public class AppConfig {

    public @Bean TransferService transferService() {
        return new TransferServiceImpl(accountRepository());
    }

    public @Bean AccountRepository accountRepository() {
        return new InMemoryAccountRepository();
    }

}

诚然,这是没有真正的 JDBC DataSource 的应用程序的一个微不足道的例子。 没关系,这篇文章的目标只是传达基本概念。 上面的 @Bean 方法将被 Spring 容器在正确的时间识别和调用,并且返回的对象将在 Spring 容器中进行管理,就像任何其他 bean 一样。 你可以看到,bean 之间的依赖关系可以简单地表示为一个 bean 方法对另一个 bean 方法的调用。 TransferServiceImpl 需要一个 AccountRepository 构造函数参数,所以只需调用 accountRepository() 方法即可。

但是,精明的 Spring 用户会看到这种情况,并问“bean 作用域呢”? 这是一个好问题。 你可能知道,所有 Spring bean 都有一个作用域。 默认情况下,bean 的作用域是“singleton”,这意味着每个 Spring 容器只有一个这样的 bean 实例。 浏览上面的代码,似乎如果我们多次调用 accountRepository(),我们实际上会创建多个实例,但事实并非如此! 当在运行时处理 @Configuration 类时,它会动态地进行子类化(使用 CGLIB),并且 @Bean 方法的子类实现得到增强,以确保尊重作用域语义。

正如你所看到的,定义 @Bean 方法非常简单。 现在,让我们引导容器并使用这些对象。

看一下 TransferServiceTest JUnit 系统测试及其 transfer100Dollars() @Test 方法。 你首先会注意到的是使用了 AnnotationConfigApplicationContext。 Spring 3 中添加了这种新的 ApplicationContext 实现,以支持直接使用 @Configuration 类实例化 Spring 容器。 该上下文是使用 AppConfig.class 作为构造函数参数创建的,之后我们使用 getBean(Class) 方法按类型检索 TransferService 和 AccountRepository bean。 该方法的其余部分只是标准的 JUnit 断言,用于执行 TransferService 和 AccountRepository API,以确保一切都按预期工作。


public class TransferServiceTest {

    @Test
    public void transfer100Dollars() {
        // create the spring container using the AppConfig @Configuration class
        ApplicationContext ctx = new AnnotationConfigApplicationContext(AppConfig.class);

        // retrieve the beans we'll use during testing
        AccountRepository accountRepository = ctx.getBean(AccountRepository.class);
        TransferService transferService = ctx.getBean(TransferService.class);

        // create accounts to test against
        accountRepository.add(new Account("A123", 1000.00));
        accountRepository.add(new Account("C456", 0.00));

        // check account balances before transfer
        assertThat(accountRepository.findById("A123").getBalance(), equalTo(1000.00));
        assertThat(accountRepository.findById("C456").getBalance(), equalTo(0.00));

        // perform transfer
        transferService.transfer(100.00, "A123", "C456");

        // check account balances after transfer
        assertThat(accountRepository.findById("A123").getBalance(), equalTo(900.00));
        assertThat(accountRepository.findById("C456").getBalance(), equalTo(100.00));
    }

}

就这样! 简单、纯 Java、类型安全配置。 我们希望你发现这是 Spring 核心依赖注入支持的一个方便而强大的补充。

当然,我们今天只是触及了表面。 使用 @Configuration 类可以做更多的事情,我们将在以后的文章中探讨这些功能。 但不要等我 - 你现在可以通过阅读 Spring 3 参考文档的 @Configuration 部分 来自己查看所有这些功能。 我鼓励大家使用这个示例项目作为一个起点,你可以从中快速测试这个新支持的其余部分

我期待你的反馈。 享受使用 @Configuration 和所有新的 Spring 3 功能,并祝你节日快乐!

  • 感谢 Erich Eichinger (半开玩笑地) 创造了“简单的旧配置”这个短语。 你可以看看他和 Spring.NET 团队正在使用他们的类似“CodeConfig”项目做的工作 在这里

获取 Spring 新闻通讯

通过 Spring 新闻通讯保持联系

订阅

取得领先

VMware 提供培训和认证,以加速你的进步。

了解更多

获得支持

Tanzu Spring 在一个简单的订阅中提供 OpenJDK™、Spring 和 Apache Tomcat® 的支持和二进制文件。

了解更多

即将举行的活动

查看 Spring 社区中所有即将举行的活动。

查看全部