2014-04-04 72 views
0

我有以下的单元测试:时的Mockito - 然后返回错误

@Test 
public void testGenerateFileName(){ 

GregorianCalendar mockCalendar = Mockito.mock(GregorianCalendar.class); 
Date date = new Date(1000); 
Mockito.when(mockCalendar.getTime()).thenReturn(date); 
... 
} 

在第三行我收到以下错误:

org.mockito.exceptions.misusing.WrongTypeOfReturnValue: Date cannot be returned by getTimeInMillis() getTimeInMillis() should return long 
*** If you're unsure why you're getting above error read on. Due to the nature of the syntax above problem might occur because: 
1. This exception *might* occur in wrongly written multi-threaded tests. Please refer to Mockito FAQ on limitations of concurrency testing. 
2. A spy is stubbed using when(spy.foo()).then() syntax. It is safer to stub spies - 
    - with doReturn|Throw() family of methods. More in javadocs for Mockito.spy() method. 

这究竟是为什么?我没有使用getTimeInMillis()

回答

3

问题是方法GregorianCalendar.getTime()是最终的,所以Mockito不能拦截方法调用。

另一种方法是使用Apache Commons Lang中的日期转换为Calendar,所以当你调用getTime它返回你所期望

DateUtils.toCalendar(date) 

如果你想要去野外,您可以使用PowerMock的值模拟最终字段,但我认为当你有一个更简单的选择时,增加PowerMock的复杂性是不值得的。

另一点。你应该尽量避免嘲笑你不拥有的对象,这对于单元测试和模拟对象来说非常重要。这里有一个reference,有一些关于这种做法的链接。

最后,因为它可能适用于您的项目:从您可以获取当前时间的时间引入“Clock”对象是一个很好的做法,测试可以操纵此时钟以返回“静态”当前时间。

编辑

的Java 8包括Clock抽象,它具有可以通过调用Clock.fixed()Clock.tick()Clock.tickSeconds()Clock.tickMinutes()获得用于测试的具体实现理想......或者你可以写自己的实现时钟。

相关问题