首页 文章

在PoolingHttpClientConnectionManager上使用apache httpclient作为jersey客户端的后端

提问于
浏览
0

我尝试使用apache httpclient作为jersey客户端的后端来自动处理cookie,这是我的代码

class ClientHelper {
  public static HttpClientConnectionManager customConnectionManager() throws Exception {
  final SSLContext sslContext = SSLContext.getInstance("SSL");

sslContext.init(null, new TrustManager[]{new X509TrustManager() {
  @Override
  public void checkClientTrusted(X509Certificate[] x509Certificates, String s)
      throws CertificateException {
    System.out.println("========checkClientTrusted=========");
  }

  @Override
  public void checkServerTrusted(X509Certificate[] x509Certificates, String s)
      throws CertificateException {
    System.out.println("========checkServerTrusted==========");
  }

  @Override
  public X509Certificate[] getAcceptedIssuers() {
    return null;
  }
}}, new SecureRandom());

SSLConnectionSocketFactory
    sslConnectionSocketFactory =
    new SSLConnectionSocketFactory(sslContext);
Registry<ConnectionSocketFactory> registry = RegistryBuilder.<ConnectionSocketFactory>create()
    .register("https", sslConnectionSocketFactory)
    .register("http", PlainConnectionSocketFactory.getSocketFactory())
    .build();
PoolingHttpClientConnectionManager phcc = new PoolingHttpClientConnectionManager(registry);
return phcc;
}

public static Client createClient() {
  HttpClient apacheClient = null;
  try {
  apacheClient =
      HttpClientBuilder.create().setConnectionManager(customConnectionManager()).build();

} catch (Exception e) {
  e.printStackTrace();
}
Client client = new Client(new ApacheHttpClient4Handler(apacheClient,
                                                        new BasicCookieStore(),
                                                        true));
return client;
  }
  }

我尝试使用apache httpclient作为jersey客户端的后端(为了处理cookie)

然后,我创建一个简单的类来测试客户端,

import com.sun.jersey.api.client.Client;
....

public class ApiTest {

  private static Client client;

  public String getAuth(String username, String passwd) {

  Map<String, String> formParams = new HashMap<String, String>();
  formParams.put("username", String.valueOf(username));
  formParams.put("passwd", String.valueOf(passwd));

try {
  String basePath = "https://xyzhost/login";

  if (client == null) {
    client = ClientHelper.createClient();
    client.addFilter(new LoggingFilter(System.out));
  }

  WebResource webResource = client.resource(basePath);

  ClientResponse response = webResource.type("application/x-www-form-urlencoded").accept("application/json")
      .post(ClientResponse.class, processFormParams(formParams));
  if (response != null) {
    String authRes = response.getEntity(String.class);
    response.close();

    return authRes;
  } else {
    return null;
  }
} catch (Exception ex) {
  ex.printStackTrace();
  return null;
}
 }


 public String getSummary(){

try {
  String basePath = "https://xyzhost/summary";

  if (client == null) {
    client = ClientHelper.createClient();
  }

  WebResource webResource = client
      .resource(basePath);

  ClientResponse response = webResource.type("application/x-www-form-urlencoded").accept("application/json")
      .post(ClientResponse.class, processFormParams(formParams));

  if (response != null) {
    String serviceRes = response.getEntity(String.class);
    response.close();
    return serviceRes;
  } else {
    return null;
  }
  } catch (Exception ex) {
    ex.printStackTrace();
    return null;
  }
}

public static void main(String[] args) throws ApiException {
  String username = "testuser";
  String passwd = "testpasswd";
  AuthApi apiTest = new ApiTest();
  String auth =apiTest.getAuth(username, passwd);
  String reslut1 = apiTest.getSummary();
  String result2 = apiTest.getSummary();
  String result3 = apiTest.getSummary();
  String result4 = apiTest.getSummary();
}
}

因此,我使用相同的客户端来命中同一主机下的服务 . 我可以成功获得“auth”和“result1”的响应,但客户端在下面的部分中停留在“result2”中

ClientResponse response = webResource.type("application/x-www-form-urlencoded").accept("application/json")
      .post(ClientResponse.class, processFormParams(formParams));

我尝试修改以下部分:

PoolingHttpClientConnectionManager phcc= new PoolingHttpClientConnectionManager(registry);
phcc.setDefaultMaxPerRoute(10);

然后,ApiTest工作,不会卡住 . 我猜这个连接有一些问题,因为默认情况下,poolingHttpClientConnectionManager的每条路由的最大值是2,所以我的ApiTest会卡在第3个请求中 . 我认为连接已经发布,因为我已经使用了响应实体,

if (response != null) {
    String serviceRes = response.getEntity(String.class);
    response.close();
    return serviceRes;
  }

但它似乎根本不起作用,连接似乎没有发布 .

谁有人可以帮忙?欣赏!

1 回答

  • 0

    我得到一个解决方案:将jersey-client的版本从1.17切换到1.18,然后问题解决了!

    <dependency>
      <groupId>com.sun.jersey</groupId>
      <artifactId>jersey-client</artifactId>
      <version>1.18</version>
      <scope>compile</scope>
    </dependency>
    

相关问题