Httpclient抛出超时等待池异常

时间:2017-11-06 05:06:08

标签: httpclient

现在我正在为我们的上传图片服务处理一个例外情况,如下所示:

我们有一个网页,来自世界各地的用户可以将他们的图像上传到我们的服务器,图像通常保持3MB左右。现在我们进行了促销,因此上传到我们服务器的图像数量非常巨大,但是导致服务器抛出异常,因为" org.apache.http.conn.ConnectionPoolTimeoutException:超时等待来自池的连接&#34 ;

我们使用apache httpclient作为核心上传中间件,其版本为4.5。*,我们使用提到的in this article方法正确处理了响应。 代码如下:

 if (returnType != StorageHttpResponse.class && response != null) {
        EntityUtils.consumeQuietly(response.getEntity());
        httpRequest.abort();
    }

此外,服务的最大连接池数为128,最大连接超时时间为50000毫秒。我们使用流模式上传图片,而不是直接上传图片文件。

所以在这里,我通过在最终代码块中使用它来正确处理响应实体,但我仍然无法停止服务抛出连接池超时异常。

我需要添加到我的服务中的任何其他内容?我是否真的使用redis为用户上传请求和发布处理排队?

这里的整个代码:

 public <T> T excute(Request request, Class<T> returnType) {
    Preconditions.checkState(!isShutDown, "JSSHttpClient is destory!");
    HttpRequestBase httpRequest = new HttpRequestBuild(this.credential).build(request);
    HttpResponse response = null;
    try {
        response = this.client.execute(httpRequest);
        if (errorHandler.hasError(request, response)) {
            int statusCode = response.getStatusLine().getStatusCode();
            log.warn("Unexpected response," + request + " http code [" + statusCode + "]");
            errorHandler.handleError(response);
        }
        if (returnType != null && returnType != StorageHttpResponse.class) {
            return JsonMessageConverter.read(returnType, response);
        }
        if (returnType == StorageHttpResponse.class) {
            return (T) new StorageHttpResponse(response);
        }
    } catch (IOException e) {
        Throwables.propagate(e);
    } finally {
        if (returnType != StorageHttpResponse.class && response != null) {
            EntityUtils.consumeQuietly(response.getEntity());
            httpRequest.abort();
        }
    }
    return null;
}

2 个答案:

答案 0 :(得分:2)

您可以在属性或 yml 文件中设置参数,如下所示。

http: 水池: 尺寸:100 套接字超时:20000 默认最大每条路由:200 最大每条路线: —— 方案:http 主机:本地主机 端口:8080 最大每条路线:100 —— 方案:https 主机:{{URL}} 端口:-1 maxPerRoute:200

答案 1 :(得分:0)

最后,我们不是通过使用代码来解决这个问题。因为我们都知道响应是否未直接使用,所以请求的连接不会被释放。所以在我们的代码中,我们首先消耗响应。

我们不是通过使用更好的代码解决了这个问题,而是根据我们的业务场景稍微修改了一些参数,如maxconnectionpoolsize,maxconnectionperroute和maxconnectiontimeout。然后运行它,现在一切都好了。希望这会对你有所帮助。