我正在为Apache HTTP客户端工作以消费服务,并且我需要根据超时和基于响应代码重试的请求。为此,我已经实施了以下代码。如何为超时和响应代码方案编写重试逻辑的JUNIT测试。我想以这样的方式编写一个单元测试,以至于当我发送任何帖子/获取请求时,如果返回429错误代码响应或任何TimeOutException,我应该确保正确执行重试逻辑。我没有关于如何为重试逻辑编写单元测试的想法。通过谷歌搜索,我找到了以下链接,但对我没有帮助。
单元测试DEFAULTHTTPREQUESTRETRYHANDLER
我正在使用Junit,Mockito来编写单元测试和PowerMock进行模拟静态方法。
public class GetClient {
private static CloseableHttpClient httpclient;
public static CloseableHttpClient getInstance() {
try {
HttpClientBuilder builder = HttpClients.custom().setMaxConnTotal(3)
.setMaxConnPerRoute(3);
builder.setRetryHandler(retryHandler());
builder.setServiceUnavailableRetryStrategy(new ServiceUnavailableRetryStrategy() {
int waitPeriod = 200;
@Override
public boolean retryRequest(final HttpResponse response, final int executionCount,
final HttpContext context) {
int statusCode = response.getStatusLine().getStatusCode();
return (((statusCode == 429) || (statusCode >= 300 && statusCode <= 399))
&& (executionCount < 3));
}
@Override
public long getRetryInterval() {
return waitPeriod;
}
});
httpclient = builder.build();
} catch (Exception e) {
//handle exception
}
return httpclient;
}
private static HttpRequestRetryHandler retryHandler() {
return (exception, executionCount, context) -> {
if (executionCount > maxRetries) {
// Do not retry if over max retry count
return false;
}
if (exception instanceof InterruptedIOException) {
// Timeout
return true;
}
if (exception instanceof UnknownHostException) {
// Unknown host
return false;
}
if (exception instanceof ConnectTimeoutException) {
// Connection refused
return false;
}
if (exception instanceof SSLException) {
// SSL handshake exception
return false;
}
HttpClientContext clientContext = HttpClientContext.adapt(context);
HttpRequest request = clientContext.getRequest();
boolean idempotent = !(request instanceof HttpEntityEnclosingRequest);
if (idempotent) {
// Retry if the request is considered idempotent
return true;
}
return false;
};
}
}
public CloseableHttpResponse uploadFile(){
CloseableHttpClient httpClient = GetClient.getInstance();
CloseableHttpResponse response = null;
try {
response = httpClient.execute(post);
} catch (Exception ex) {
//handle exception
}
return response;
}
任何人都可以帮助我。
您的httpclient具有" target" URL,可以说localhost:1234。您要测试的是重试代码,因此您不应该触摸httpclient本身(因为这不是您的组件,因此也不需要测试它。(
因此,问题的问题是当您的Localhost:1234响应是有问题的,您想看到将运行的重试逻辑(不是您的实现。您唯一要做的就是嘲笑" Localhost:1234"!
此工具http://wiremock.org/是这样做的理想选择。您可以为目标URL创建存根,并根据几乎所有喜欢的内容提供一系列响应。
您的代码应该看起来像在致电uploadFile
stubFor(post(urlEqualTo("/hash"))
.willReturn(aResponse()
.withStatus(200)
.withBody(externalResponse)));
和致电uploadFile
并验证步骤以验证到达模拟端点的模拟请求
Assert.assert* //... whatever you want to assert in your handlers / code / resposnes
verify(postRequestedFor(urlEqualTo("/hash")));