因此,如果我从回调方法内部调用任何失败的JUnit断言,我会得到以下异常:
Mar 12, 2012 11:24:41 AM
com.gargoylesoftware.htmlunit.javascript.background.JavaScriptJobManagerImpl runJob
SEVERE: Job run failed with unexpected RuntimeException: [object Class JavaObject] (injected script#14)
net.sourceforge.htmlunit.corejs.javascript.JavaScriptException: [object Class JavaObject] (injected script#14)
at net.sourceforge.htmlunit.corejs.javascript.Interpreter.interpretLoop(Interpreter.java:1062)
at script(injected script:14)
at net.sourceforge.htmlunit.corejs.javascript.Interpreter.interpret(Interpreter.java:845)
at net.sourceforge.htmlunit.corejs.javascript.InterpretedFunction.call(InterpretedFunction.java:164)
at net.sourceforge.htmlunit.corejs.javascript.ContextFactory.doTopCall(ContextFactory.java:429)
at com.gargoylesoftware.htmlunit.javascript.HtmlUnitContextFactory.doTopCall(HtmlUnitContextFactory.java:269)
at net.sourceforge.htmlunit.corejs.javascript.ScriptRuntime.doTopCall(ScriptRuntime.java:3162)
at net.sourceforge.htmlunit.corejs.javascript.InterpretedFunction.call(InterpretedFunction.java:162)
at com.gargoylesoftware.htmlunit.javascript.JavaScriptEngine.callFunction(JavaScriptEngine.java:559)
at com.gargoylesoftware.htmlunit.javascript.host.xml.XMLHttpRequest.setState(XMLHttpRequest.java:181)
at com.gargoylesoftware.htmlunit.javascript.host.xml.XMLHttpRequest.doSend(XMLHttpRequest.java:525)
at com.gargoylesoftware.htmlunit.javascript.host.xml.XMLHttpRequest.access$000(XMLHttpRequest.java:64)
at com.gargoylesoftware.htmlunit.javascript.host.xml.XMLHttpRequest$1.run(XMLHttpRequest.java:461)
at net.sourceforge.htmlunit.corejs.javascript.Context.call(Context.java:537)
at net.sourceforge.htmlunit.corejs.javascript.ContextFactory.call(ContextFactory.java:538)
at com.gargoylesoftware.htmlunit.javascript.host.xml.XMLHttpRequest$2.run(XMLHttpRequest.java:467)
at com.gargoylesoftware.htmlunit.javascript.background.JavaScriptJobManagerImpl.runJob(JavaScriptJobManagerImpl.java:226)
at com.gargoylesoftware.htmlunit.javascript.background.JavaScriptJobManagerImpl.runSingleJob(JavaScriptJobManagerImpl.java:307)
at com.gargoylesoftware.htmlunit.javascript.background.JavaScriptExecutor.run(JavaScriptExecutor.java:182)
at java.lang.Thread.run(Thread.java:722)
一个简单的测试可以产生这个:
public void testSimple() {
MyPrgrmServiceAsync serv = GWT.create(MyPrgrmService.class);
serv.search("some query", new AsyncCallback<SearchResult>() {
public void onSuccess(SearchResult sr) {
fail();
}
public void onFailure(Throwable caught) {
fail(caught.toString());
}
});
delayTestFinish(60000);
}
当这个测试运行时,它"通过"了JUnit Runner对Eclipse中显示的绿色条的关注,但显然它应该失败。出现任何问题的唯一迹象是控制台中的异常。如果我把fail()移到回调之外,它会正常失败,并表明是这样。此外,解析为true的断言行为正常,所以测试似乎根本不知道如何检测匿名类中出现的故障。关于如何在GWTTestCase的回调/匿名类中使用JUnit断言,我是否有一些理解不正确的地方?
您的基本理解似乎是正确的-delayTestFinish
的任务是不允许测试通过,除非在给定的毫秒数内(在您的情况下为60秒)调用finishTest()。在任何一个回调方法中都不需要调用finishTest()
,因为fail
将抛出异常(如果代码达到了那个程度)。
你确定测试成功完成了吗?如前所述,如果配置错误,调用从未到达服务器,或者服务器从未返回,则无法调用fail
和finishTest
,因此测试方法无法通过。请确保等待整整60秒后才接受"通过"的结果-如果从未调用finishTest
,则测试方法将不会被视为完成,或者应该将其视为失败。
也就是说,这个异常是很有用的——这是在模拟浏览器-htmlunit中——而这个异常是"浏览器"中出现的问题。从简短的跟踪和没有其他日志语句来看,很难说到底出了什么问题。你也可以考虑在真实的浏览器中运行它,看看是否出现了更有用的错误-请查看http://code.google.com/webtoolkit/doc/latest/DevGuideTestingRemoteTesting.html了解如何在常规浏览器中以dev或prod模式运行测试。
另一种想法可能是向GWT注册一个未捕获的异常处理程序,看看会发生什么——可能是其他异常正在扼杀测试,并以某种方式阻止delayTestFinish正常运行(尽管我从未听说过这样的事情)。
GWT.setUncaughtExceptionHandler(new UncaughtExceptionHandler() {
public void onUncaughtException(Throwable e) {
fail(e.getMessage());
}
});
问题是我在gwtStUP()中调用finishTest()。我在那里运行了一些初始化代码,这是一个异步方法,我想确保它在实际测试代码之前完成,但事实证明,它只是在实际测试之前完成了测试。这个故事的寓意是:不要对你的finishTest()位置感到愚蠢。