如何为Spring测试创建TestContext?

14
我有一个相对较小的Java库,其中实现了几十个bean(没有数据库或GUI)。我创建了一个Spring Bean配置文件,其他Java项目使用它将我的bean注入到他们的东西中。
现在,我首次尝试使用Spring Test将其中一些bean注入到我的junit测试类中(而不是仅仅实例化它们)。
我这样做部分原因是为了学习Spring Test,部分原因是为了强制测试使用我提供给其他人的相同的bean配置文件。
在Spring文档中说,我需要使用Spring附带的“TestContext”类创建应用程序上下文。我认为应该在一个XML文件中完成这个操作,并通过我的测试类上的@ContextConfiguration注释引用该文件。
@ContextConfiguration({"/test-applicationContext.xml"})

然而,并没有提示文件里应该放什么内容!

当我在Eclipse中运行测试时,它会出现错误"failed to load Application Context"....当然。

更新:

这是test-applicationContext.xml文件:

<?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-3.0.xsd">
    <description>Holds application context for testing of the domain module.</description>

    <!-- Imports the uuid generator bean definitions -->
    <import resource="resources/domain-uuid.xml"/>  
</beans>
我的项目目录长这样:
domain/
   src/
      main/
         java/
         resources/
      test/
         java/
         resources/ (location of test-applicationContext.xml)

仅出于好玩,我也尝试通过 "mvn clean test" 从命令行构建,但是我得到了以下错误,这可能是我的真正问题:

package org.springframework.test.context does not exist

package org.springframework.test.context.junit4 does not exist

cannot find symbol
symbol: class ContextConfiguration
@ContextConfiguration({"/resources/test-applicationContext.xml"})

cannot find symbol
symbol: class SpringJUnit4ClassRunner
@RunWith(SpringJUnit4ClassRunner.class)
2个回答

12

在应用程序上下文文件中放置什么。 TestContext框架的工作方式是允许您在集成测试的上下文中重用应用程序的连接。因此,在大多数情况下,您不需要在应用程序上下文配置文件中放置任何特殊的测试内容。如果您的控制器在应用程序中具有服务bean依赖项,则在集成测试中也将具有该依赖项。如果您的DAO在应用程序中具有SessionFactory,则在集成测试中也是如此。这样,当您编写集成测试时,就不必再次进行所有这些连接。非常酷。

我之前说过在大多数情况下,因为至少有一个例外值得一提。通常,您的应用程序将使用JNDI来定位数据源,但在集成测试中(至少在容器外的集成测试中),您通常不会有可用的JNDI环境。因此,您应该将DataSource bean的创建隔离到单独的文件中,并为您的实际应用程序使用JNDI版本,为您的集成测试使用非JNDI版本(例如,只需创建一个直接的BasicDataSource)。以下是前者的示例:

<jee:jndi-lookup id="dataSource" jndi-name="jdbc/myStoreDS" resource-ref="true"/>

这里是后者的一个例子:

<bean id="dataSource"
    class="org.apache.commons.dbcp.BasicDataSource"
    destroy-method="close"
    p:driverClassName="${dataSource.driverClassName}"
    p:url="${dataSource.url}"
    p:username="${dataSource.username}"
    p:password="${dataSource.password}" />

这些将放在单独的文件中。第一个可能放在beans-datasource.xml中供普通应用程序使用,第二个放在beans-datasource-it.xml中供集成测试使用。对于普通应用程序使用和集成测试都适用的配置(即大多数情况下的bean配置),应放在一个公共的配置文件或多个配置文件中。

此外,Spring 3引入了一个新的jdbc命名空间,允许您创建嵌入式数据库,例如HSQLDB数据库或Derby数据库等。它的使用方式如下:

<jdbc:embedded-database id="dataSource">
    <jdbc:script location="classpath:hsql/schema.sql" />
    <jdbc:script location="classpath:hsql/test-data.sql" />
</jdbc:embedded-database>

如果您想使用它,那么这将替换上面描述的BasicDataSource配置。

为什么会出现错误。您看到的错误是因为您的@ContextConfiguration值隐含地指示应用程序上下文文件应该在类路径上。 重要提示:删除/resources部分。这是Maven内部机制;当它构建您的JAR或WAR时,它会将resources目录的内容复制到您的类路径中,而不是resources本身。这应该有所帮助。

编辑:

为了解决“找不到符号”的错误,您需要将测试依赖项添加到Maven POM中。这将包括JUnit和Spring Test模块,两者都具有<scope>test</scope>。此外,如果您正在使用像Mockito这样的模拟框架,您还需要将该依赖项(具有测试范围)添加到POM中。请尝试并报告发生了什么。


抱歉 - 我没有使用JNDI或DAO。我不知道在哪里创建textContext!你说“应用程序上下文文件” - 那是什么? - Dave
"应用上下文文件"就是指你的Spring配置XML文件。这个文件必须具有一个顶层<beans>元素。你可以直接将它放在WEB-INF目录下,也可以将它放在类路径下,比如像你在其他评论中所说的src/test/resource下。为了更好地帮助你解决问题,建议你在原始帖子中添加目录结构(相关部分),并展示你的test-applicationContext.xml文件的内容。 - user41871
1
好的 - 我想我明白了。我不需要在任何地方指定TestContext。Spring会以某种方式“知道”(怎么知道的?)。问题是Spring找不到我的配置文件。 - Dave
1
不错,Spring将会处理TestContext部分。开发者通常不需要在TestContext上进行任何操作。这只是测试框架用来管理有关测试用例(由测试类实现)和当前运行的测试(由测试方法实现)的上下文信息的。因此,如果您在测试方法上使用了@DirtiesContext注释,那么框架会将应用程序上下文(即您的bean容器)标记为脏状态,以便在运行测试后重新加载它。 - user41871

9

如果要直接在src/test/resources下找到它,请将其更改为:

@ContextConfiguration({"classpath:/test-applicationContext.xml"})

如果您没有指定任何内容,那么Spring将在测试类所在的同一包中进行搜索。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接