2013-02-18 69 views
0

我有一个带有JSF页面的maven WAR包。通常我使用如何在Junit中调用数据源

@Resource(name = "jdbc/Oracle") 
    private DataSource ds; 

当我在Glassfish服务器上部署WAR包时调用数据库。但在JUnit测试中,当我使用netbeans在我的笔记本电脑上构建包时,我无法使用此数据源。 我该如何解决这个问题?我想在构建包后立即运行带有数据库表的JUnit测试,但没有数据源。 什么是可能的解决方案?

回答

3

你真的想对数据库运行你的单元测试吗?就我个人而言,我会尽量避免这种情况,因为它通常将测试与数据库状态紧密联系在一起,并且经常会阻止您实际测试“单元”以及您可能想要处理的所有可能状态。它也可能会让你的单元测试花费一些时间来运行,这并不理想。

另一种方法是创建一个模拟DataSource,例如使用EasyMockMockito。或者你可以创建自己的DataSource接口的模拟实现,如果你知道你想在很多测试中定义DataSources的一些常见行为。

如果你真的想使用数据库,你必须手动实例化你正在使用的DataSource的任何实现(例如OracleDataSource),然后在你的类中使用它。

无论哪种情况,您都可能必须切换到使用constructor or method injection才能更容易在要测试的实例上设置DataSource。 (否则,你将不得不使用反射来设置私有变量。)

例如,你的类可能是这样的:

public class DatabaseOperations { 
    private DataSource dataSource; 

    @Resource(name = "jdbc/Oracle") 
    public void setDataSource(DataSource dataSource) { 
     this.dataSource = dataSource; 
    } 
} 

然后测试可能是这样的:

public class DatabaseOperationsTest { 
    public void testSomeOperation() { 
     DatabaseOperations databaseOperations = new DatabaseOperations(); 
     databaseOperations.setDataSource(new MockDataSource()); 
    } 
} 
1

如果确实需要使用注入的数据源来运行测试,那么可以考虑使用Arquillian,它将为您创建一个部署单元,将其部署到嵌入式或远程Glassfish容器,以及配置的专用于测试的DataSource无线SH。对于这种特定场景,他们有一个guide

优势是你将拥有一个拥有CDI的成熟容器。您可以控制获取软件包的内容,以便为CDI类提供测试存根。您还可以控制部署配置(测试与生产配置)。它是非侵入性的。