【问题标题】:Dependency Injection Does not work in Models or Tests in Play Framework 2.4.x依赖注入在 Play Framework 2.4.x 中的模型或测试中不起作用
【发布时间】:2016-01-21 18:56:32
【问题描述】:

我正在尝试为我的 Play Framework 2.4.6 应用程序编写一些单元测试。我需要 WS 用于我的目的测试。但是,当我使用文档的方法注入 WS 时,如果在测试或模型中使用,我最终会得到一个空指针。但是,如果我将它安装到我的一个控制器中,注入会完美运行。

这是我的测试:

import org.junit.Test;
import play.test.WithServer;
import play.libs.ws.*;
import javax.inject.Inject;
import static play.test.Helpers.running;
import static play.test.Helpers.testServer;

public class UserProfileTests extends WithServer {
    @Inject
    WSClient ws;

    @Test
    public void demographicTest() {

        System.out.println(ws.toString()); //null pointer exception

        running(testServer(3333), () -> {
            System.out.println(ws.toString()); //null pointer exception
        });

    }
}

这是运行激活器测试时的控制台输出

[error] Test UserProfileTests.demographicTest failed: java.lang.NullPointerException: null, took 5.291 sec
[error]     at UserProfileTests.demographicTest(UserProfileTests.java:15)
[error]     ...
[error] Failed: Total 4, Failed 1, Errors 0, Passed 3
[error] Failed tests:
[error]     UserProfileTests
[error] (test:test) sbt.TestsFailedException: Tests unsuccessful
[error] Total time: 9 s, completed Jan 21, 2016 11:54:49 AM

我确定我只是从根本上误解了有关依赖注入或系统工作原理的一些东西。任何帮助将不胜感激。

【问题讨论】:

    标签: java unit-testing playframework dependency-injection


    【解决方案1】:

    由于测试应该只专注于一个特定的扫描/对象,我认为您无需担心如何为您的测试进行依赖注入,而只需实例化您需要的内容。这是使用应用程序Injector 进行实例化的一种方法:

    import org.junit.Before;
    import org.junit.Test;
    import play.libs.ws.WSClient;
    import play.test.WithServer;
    
    public class UserProfileTests extends WithServer {
    
        private WSClient ws;
    
        @Before
        public void injectWs() {
            ws = app.injector().instanceOf(WSClient.class);
        }
    
        @Test
        public void demographicTest() {
            System.out.println(ws);
        }
    }
    

    但是,当然,您也可以手动实例化 ws,或者根据需要模拟它。

    关于models,Guice 不处理它们的生命周期,因此没有直接的方法在模型上进行依赖注入。你总能找到一种方法来做到这一点,但你应该吗?如果尝试从数据库中加载 100 个对象,然后必须在每个对象中注入依赖项,会发生什么?

    除了(可能的)性能问题之外,也许您在这里还违反了Single Responsibility Principle,并且您的模型正在做很多工作。

    【讨论】:

    • 感谢您提供信息丰富的回复。我真的很感激。
    • @marcospereira 通常注入 WSClient 的正确方法应该是什么(不是在测试中,我的意思是在应用程序中)?我不认为将它注入控制器(未使用)然后必须将其作为构造函数参数传递给服务是一个不错的设计。
    猜你喜欢
    • 2015-12-16
    • 1970-01-01
    • 1970-01-01
    • 2015-10-08
    • 2015-09-30
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多