java httpclient 4.x性能指南解决问题

Bam*_*ylo 1 java performance apache-httpclient-4.x

有一篇很好的文章http://hc.apache.org/httpclient-3.x/performance.html与http性能,池等有关,对于最新的4.x版本找不到相同的文章.有没有人看到它?我在重负载下遇到了性能问题并希望解决它们.我正在使用4.1版本.这是分析器输出:

26% org.apache.http.impl.client.CloseableHttpClient.execute(multiple parameter matches) :26,107,40
26% org.apache.http.impl.client.CloseableHttpClient.execute(org.apache.http.client.methods.HttpUriRequest, org.apache.http.protocol.HttpContext) :82,46
26% org.apache.http.impl.client.AbstractHttpClient.doExecute(org.apache.http.HttpHost, org.apache.http.HttpRequest, org.apache.http.protocol.HttpContext) :882,818
26% org.apache.http.impl.client.AbstractHttpClient.createHttpContext() :301
26% org.apache.http.impl.client.AbstractHttpClient.getConnectionManager() :484
26% org.apache.http.impl.client.AbstractHttpClient.createClientConnectionManager() :321
26% org.apache.http.impl.conn.SchemeRegistryFactory.createDefault() :52
26% org.apache.http.conn.ssl.SSLSocketFactory.getSocketFactory() :168
26% org.apache.http.conn.ssl.SSLContexts.createDefault() :58
26% javax.net.ssl.SSLContext.init(javax.net.ssl.KeyManager[], javax.net.ssl.TrustManager[], java.security.SecureRandom) :283
26% sun.security.ssl.SSLContextImpl.engineInit(javax.net.ssl.KeyManager[], javax.net.ssl.TrustManager[], java.security.SecureRandom) :83,92
26% javax.net.ssl.TrustManagerFactory.init(java.security.KeyStore) :250
26% sun.security.ssl.TrustManagerFactoryImpl.engineInit(java.security.KeyStore) :51
26% sun.security.ssl.TrustManagerFactoryImpl.getCacertsKeyStore(java.lang.String) :221
26% java.security.KeyStore.load(java.io.InputStream, char[]) :1214
26% sun.security.provider.JavaKeyStore$JKS.engineLoad(java.io.InputStream, char[]) :55
26% sun.security.provider.JavaKeyStore.engineLoad(java.io.InputStream, char[]) :723,747
26% java.security.cert.CertificateFactory.generateCertificate(java.io.InputStream) :339
26% sun.security.provider.X509Factory.engineGenerateCertificate(java.io.InputStream) :93
26% sun.security.provider.X509Factory.getFromCache(sun.security.util.Cache, byte[]) :203
Run Code Online (Sandbox Code Playgroud)

我有4种方法使用httpclient通过HTTP发送一些数据,每种方法占用总时间的25%.剩下的处理需要毫秒.看起来我正在以错误的方式使用httpclient.

编辑:参见oleg答案+阅读https://hc.apache.org/httpcomponents-client-ga/tutorial/html/connmgmt.html 回答所有相关问题

主要部分是:建立联合经理的好方法

PoolingHttpClientConnectionManager cm = new PoolingHttpClientConnectionManager();
// Increase max total connection to 200
cm.setMaxTotal(200);
// Increase default max connection per route to 20
cm.setDefaultMaxPerRoute(20);
// Increase max connections for localhost:80 to 50
HttpHost localhost = new HttpHost("locahost", 80);
cm.setMaxPerRoute(new HttpRoute(localhost), 50);

CloseableHttpClient httpClient = HttpClients.custom()
        .setConnectionManager(cm)
        .build();
Run Code Online (Sandbox Code Playgroud)

一种同时使用HttpClient的方法

//While HttpClient instances are thread safe and can be shared
//between multiple threads of execution, it is highly recommended that 
//each thread maintains its own dedicated instance of HttpContext .


static class GetThread extends Thread {

    private final CloseableHttpClient httpClient;
    private final HttpContext context;
    private final HttpGet httpget;

    public GetThread(CloseableHttpClient httpClient, HttpGet httpget) {
        this.httpClient = httpClient;
        this.context = HttpClientContext.create();
        this.httpget = httpget;
    }

    @Override
    public void run() {
        try {
            CloseableHttpResponse response = httpClient.execute(
                    httpget, context);
            try {
                HttpEntity entity = response.getEntity();
            } finally {
                response.close();
            }
        } catch (ClientProtocolException ex) {
            // Handle protocol errors
        } catch (IOException ex) {
            // Handle I/O errors
        }
    }

}
Run Code Online (Sandbox Code Playgroud)

ok2*_*k2c 7

主要建议仍与3.1相同

请重新使用HttpClient实例!HttpClient实例非常昂贵.抛弃它不仅会丢弃实例本身,还会抛弃SSL上下文,连接管理器以及连接管理器可能保持活动的所有持久连接.

  • 应该在不再需要时关闭HttpClient实例.在使用实例时,应该关闭响应对象以确保正确释放连接回池 (2认同)
  • 我发现释放每个呼叫的连接可以防止连接泄漏。httpget.releaseConnection().. (2认同)