我试图模拟一个私有方法的输出,该输出在另一个私有方法中被调用,我别无选择,只能测试后面的私有方法,因此我添加了可以在这里表示的示例测试代码,
此示例类
package com.testableClass;
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
public class TestableClass {
private int initialMockMethod(Object obj)
{
System.out.println(" ++++ Came Here ++++ ");
String str = getRestString("");
System.out.println("str ="+str);
return str.length();
}
private String getRestString(String abc)
{
String output="";
try {
URL url = new URL("https://gorest.co.in/public-api/users");//your url i.e fetch data from .
HttpURLConnection conn = (HttpURLConnection) url.openConnection();
conn.setRequestMethod("GET");
conn.setRequestProperty("Accept", "application/json");
if (conn.getResponseCode() != 200) {
throw new RuntimeException("Failed : HTTP Error code : "
+ conn.getResponseCode());
}
InputStreamReader in = new InputStreamReader(conn.getInputStream());
BufferedReader br = new BufferedReader(in);
while ((output = br.readLine()) != null) {
System.out.println(output);
}
conn.disconnect();
return output;
} catch (Exception e) {
System.out.println("Exception in NetClientGet:- " + e);
}
return abc;
}
}
现在是此PowerMock类
package com.testableClass;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.Mockito;
import org.powermock.api.mockito.PowerMockito;
import org.powermock.core.classloader.annotations.PrepareForTest;
import org.powermock.modules.junit4.PowerMockRunner;
import org.powermock.reflect.Whitebox;
import junit.framework.Assert;
@RunWith(PowerMockRunner.class)
@PrepareForTest(fullyQualifiedNames = "com.testableClass.TestableClass")
public class PowerMockTest {
@Test
public void testPrivateMethod() throws Exception
{
String message = "Hello PowerMockito";
String expectation = "Expectation";
TestableClass mock = PowerMockito.spy(new TestableClass());
// PowerMockito.doReturn(expectation).when(mock, "getRestString", message);
PowerMockito.when(mock, "getRestString", message).thenReturn(expectation);
int count = Whitebox.invokeMethod(mock, "initialMockMethod", new Object());
System.out.println(" +++ Count : "+count+" ++++ ");
Assert.assertTrue(true);
}
}
我的问题是当我运行测试用例时
PowerMockito.when(mock, "getRestString", message).thenReturn(expectation);
执行原始方法并返回原始输出,而我的要求是,
当我的测试用例实际上正在调用私有方法 initialMockMethod 时,不应调用 getRestString ,而应返回我模拟的预期输出,即“
答案 0 :(得分:0)
我会说不要尝试模拟私有方法,而不是使用反射和PowerMock。这是该类的隐藏细节。
我的建议是,如果您的方法发出HTTP请求,则让它执行。但是您可以使用模拟服务器模拟响应。但是要做到这一点,您需要将端点设置为外部,以便可以将其注入。
我稍微改变了你的班级;还是一样的目的。
public class TestableClass {
private final String resourceUrl;
public TestableClass(String resourceUrl) {
this.resourceUrl = resourceUrl;
}
public int publicMethod() {
return initialMockMethod(null);
}
private int initialMockMethod(Object obj) {
var str = getRestString("");
return str.length();
}
private String getRestString(String abc) {
try {
var url = new URL(resourceUrl);
var conn = (HttpURLConnection) url.openConnection();
conn.setRequestMethod("GET");
conn.setRequestProperty("Accept", "application/json");
if (conn.getResponseCode() != 200) {
throw new RuntimeException("Failed : HTTP Error code : "
+ conn.getResponseCode());
}
var in = new InputStreamReader(conn.getInputStream());
var br = new BufferedReader(in);
var result = br.lines().collect(Collectors.joining("\n"));
conn.disconnect();
return result;
} catch (Exception e) {
System.out.println("Exception in NetClientGet:- " + e);
}
return abc;
}
}
这是测试
public class TestingTestableClass {
@Test
@SneakyThrows
public void test() {
final var server = new MockWebServer();
server.start(9999);
var instance = new TestableClass("http://127.0.0.1:9999");
server.enqueue(
new MockResponse()
.setResponseCode(200)
.setBody("this is the response")
);
final int result = instance.publicMethod();
Assertions.assertEquals(
"this is the response".length(),
result
);
final var record = server.takeRequest();
final var method = record.getMethod();
Assertions.assertEquals("GET", method);
server.shutdown();
}
}
签出MockWebServer here