我想用Mockito测试以下代码:
public static String funcToTest(String query) throws Exception {
String url = Config.getURL(serviceName);
HttpClient client = new HttpClient();
HttpMethod method = new GetMethod(url);
String resultantString= "";
method.setQueryString(URIUtil.encodeQuery(query));
client.executeMethod(method);
if (method.getStatusCode() == HttpStatus.SC_OK) {
Reader reader = new InputStreamReader(method
.getResponseBodyAsStream());
int charValue = 0;
StringBuffer sb = new StringBuffer(1024);
while ((charValue = reader.read()) != -1) {
sb.append((char) charValue);
}
resultantString = sb.toString();
}
method.releaseConnection();
return resultantString;
}
我创建了如下测试:
@Test
public void testFunc() throws Exception{
HttpMethod method = Mockito.mock(HttpMethod.class);
InputStream inputStream = Mockito.mock(InputStream.class);
Reader reader = Mockito.mock(Reader.class);
when(method.getResponseBodyAsStream()).thenReturn(inputStream);
PowerMockito.whenNew(Reader.class).withArguments(eq(inputStream)).thenReturn(reader);
Mockito.when(reader.read()).thenReturn((int)'1', -1);
String actualResult = cls.funcToTest("");
String expected = "1";
assertEquals(expected, actualResult);
}
但是reader.read()
方法没有返回1.相反,它总是返回-1。我应该如何模拟Reader
以便read()
方法将返回-1以外的其他内容。
感谢。
答案 0 :(得分:1)
首先,您的测试代码正在进行大量.class
模拟以模拟函数局部变量/引用。模拟用于类依赖,而不用于函数局部变量。
如上所述,您无法单独使用模拟来测试您的函数funcToTest
。如果不愿意使用真实对象,则需要重写此函数 - HttpMethod
& Reader
。
如果您希望模拟对这些对象的调用并使用此get方法替换new
的代码,则需要在此函数外部使用new
删除对象创建代码。 e.g。
protected HttpMethod getHttpMethod(String Url){
return new GetMethod(url);
}
另外,我没有看到你嘲笑这一行的虚假URL - 这似乎是单元测试的必要条件。
String url = Config.getURL(serviceName);
在函数外部创建对象创建代码之后,您需要创建一个新类而不是扩展您的SUT
(测试对象)并覆盖这些方法(getHttpMethod
)以提供伪造/模拟实例
您需要编写类似的方法来获取Reader
实例。
然后你测试这个新类 - 从你的SUT扩展,因为不需要测试对象创建逻辑。
如果不在函数外部使用对象创建代码,我就不会看到mockito模仿它的方法。
希望它有所帮助!!
答案 1 :(得分:0)
它必须有效,对不起是什么让你有点困惑)
// annotations is very important, cls I your tested class name, i assume cls is yours
@RunWith(PowerMockRunner.class)
@PrepareForTest({cls.class})
public class PrinterTest {
@Test
public void print() throws Exception {
String url = "";
GetMethod method = Mockito.mock(GetMethod.class);
InputStream inputStream = Mockito.mock(InputStream.class);
InputStreamReader reader = Mockito.mock(InputStreamReader.class);
Mockito.when(method.getResponseBodyAsStream()).thenReturn(inputStream);
//forgot about it )
PowerMockito.whenNew(GetMethod.class).withArguments(eq(url)).thenReturn(method);
PowerMockito.whenNew(InputStreamReader.class).withArguments(eq(inputStream)).thenReturn(reader);
Mockito.when(reader.read()).thenReturn((int) '1', -1);
when(method.getStatusCode()).thenReturn(HttpStatus.SC_OK);
String actualResult = cls.funcToTest(url);
String expected = "1";
assertEquals(expected, actualResult);
}
}