Use httpcomponents fluent API in acceptance tests

By using the fluent API we can simplify the HTTP connection calls.

We no longer need to explicitly set the max connections per route and
max total connections. Internally the fluent API's Executor [1] uses
a PoolingHttpClientConnectionManager with maximum 100 connections per
route and a total maximum of 200 connections. These maximums are not
as high as the ones we were previously using, but those were most
likely over-estimated anyway.

[1] http://hc.apache.org/httpcomponents-client-ga/fluent-hc/apidocs/org/apache/http/client/fluent/Executor.html

Change-Id: Ibab7ff76736f9ba063df28addc9a786bbaaadfe7
diff --git a/gerrit-acceptance-tests/BUCK b/gerrit-acceptance-tests/BUCK
index b6a7b29..f4fbd2c 100644
--- a/gerrit-acceptance-tests/BUCK
+++ b/gerrit-acceptance-tests/BUCK
@@ -29,6 +29,7 @@
     '//lib:truth',
 
     '//lib/auto:auto-value',
+    '//lib/httpcomponents:fluent-hc',
     '//lib/httpcomponents:httpclient',
     '//lib/httpcomponents:httpcore',
     '//lib/log:impl_log4j',
diff --git a/gerrit-acceptance-tests/src/test/java/com/google/gerrit/acceptance/HttpSession.java b/gerrit-acceptance-tests/src/test/java/com/google/gerrit/acceptance/HttpSession.java
index f765e7a..1e0920e 100644
--- a/gerrit-acceptance-tests/src/test/java/com/google/gerrit/acceptance/HttpSession.java
+++ b/gerrit-acceptance-tests/src/test/java/com/google/gerrit/acceptance/HttpSession.java
@@ -16,12 +16,9 @@
 
 import com.google.common.base.CharMatcher;
 
-import org.apache.http.auth.AuthScope;
-import org.apache.http.auth.UsernamePasswordCredentials;
-import org.apache.http.client.HttpClient;
-import org.apache.http.client.methods.HttpGet;
-import org.apache.http.impl.client.BasicCredentialsProvider;
-import org.apache.http.impl.client.HttpClientBuilder;
+import org.apache.http.HttpHost;
+import org.apache.http.client.fluent.Executor;
+import org.apache.http.client.fluent.Request;
 
 import java.io.IOException;
 import java.net.URI;
@@ -29,33 +26,18 @@
 public class HttpSession {
 
   protected final String url;
-  private final TestAccount account;
-  private HttpClient client;
+  private final Executor executor;
 
   public HttpSession(GerritServer server, TestAccount account) {
     this.url = CharMatcher.is('/').trimTrailingFrom(server.getUrl());
-    this.account = account;
+    URI uri = URI.create(url);
+    this.executor = Executor
+        .newInstance()
+        .auth(new HttpHost(uri.getHost(), uri.getPort()),
+            account.username, account.httpPassword);
   }
 
-  public HttpResponse get(String path) throws IOException {
-    HttpGet get = new HttpGet(url + path);
-    return new HttpResponse(getClient().execute(get));
-  }
-
-  protected HttpClient getClient() {
-    if (client == null) {
-      URI uri = URI.create(url);
-      BasicCredentialsProvider creds = new BasicCredentialsProvider();
-      creds.setCredentials(new AuthScope(uri.getHost(), uri.getPort()),
-          new UsernamePasswordCredentials(account.username,
-              account.httpPassword));
-      client = HttpClientBuilder
-          .create()
-          .setDefaultCredentialsProvider(creds)
-          .setMaxConnPerRoute(512)
-          .setMaxConnTotal(1024)
-          .build();
-    }
-    return client;
+  protected RestResponse execute(Request request) throws IOException {
+    return new RestResponse(executor.execute(request).returnResponse());
   }
 }
diff --git a/gerrit-acceptance-tests/src/test/java/com/google/gerrit/acceptance/RestSession.java b/gerrit-acceptance-tests/src/test/java/com/google/gerrit/acceptance/RestSession.java
index e06d31f..98459b3 100644
--- a/gerrit-acceptance-tests/src/test/java/com/google/gerrit/acceptance/RestSession.java
+++ b/gerrit-acceptance-tests/src/test/java/com/google/gerrit/acceptance/RestSession.java
@@ -21,10 +21,7 @@
 import com.google.gerrit.server.OutputFormat;
 
 import org.apache.http.Header;
-import org.apache.http.client.methods.HttpDelete;
-import org.apache.http.client.methods.HttpGet;
-import org.apache.http.client.methods.HttpPost;
-import org.apache.http.client.methods.HttpPut;
+import org.apache.http.client.fluent.Request;
 import org.apache.http.entity.BufferedHttpEntity;
 import org.apache.http.entity.InputStreamEntity;
 import org.apache.http.entity.StringEntity;
@@ -41,7 +38,6 @@
     super(server, account);
   }
 
-  @Override
   public RestResponse get(String endPoint) throws IOException {
     return getWithHeader(endPoint, null);
   }
@@ -53,11 +49,11 @@
 
   private RestResponse getWithHeader(String endPoint, Header header)
       throws IOException {
-    HttpGet get = new HttpGet(url + "/a" + endPoint);
+    Request get = Request.Get(url + "/a" + endPoint);
     if (header != null) {
       get.addHeader(header);
     }
-    return new RestResponse(getClient().execute(get));
+    return execute(get);
   }
 
   public RestResponse put(String endPoint) throws IOException {
@@ -75,28 +71,28 @@
 
   public RestResponse putWithHeader(String endPoint, Header header,
       Object content) throws IOException {
-    HttpPut put = new HttpPut(url + "/a" + endPoint);
+    Request put = Request.Put(url + "/a" + endPoint);
     if (header != null) {
       put.addHeader(header);
     }
     if (content != null) {
       put.addHeader(new BasicHeader("Content-Type", "application/json"));
-      put.setEntity(new StringEntity(
+      put.body(new StringEntity(
           OutputFormat.JSON_COMPACT.newGson().toJson(content),
           Charsets.UTF_8.name()));
     }
-    return new RestResponse(getClient().execute(put));
+    return execute(put);
   }
 
   public RestResponse putRaw(String endPoint, RawInput stream) throws IOException {
     Preconditions.checkNotNull(stream);
-    HttpPut put = new HttpPut(url + "/a" + endPoint);
+    Request put = Request.Put(url + "/a" + endPoint);
     put.addHeader(new BasicHeader("Content-Type", stream.getContentType()));
-    put.setEntity(new BufferedHttpEntity(
+    put.body(new BufferedHttpEntity(
         new InputStreamEntity(
             stream.getInputStream(),
             stream.getContentLength())));
-    return new RestResponse(getClient().execute(put));
+    return execute(put);
   }
 
   public RestResponse post(String endPoint) throws IOException {
@@ -104,19 +100,18 @@
   }
 
   public RestResponse post(String endPoint, Object content) throws IOException {
-    HttpPost post = new HttpPost(url + "/a" + endPoint);
+    Request post = Request.Post(url + "/a" + endPoint);
     if (content != null) {
       post.addHeader(new BasicHeader("Content-Type", "application/json"));
-      post.setEntity(new StringEntity(
+      post.body(new StringEntity(
           OutputFormat.JSON_COMPACT.newGson().toJson(content),
           Charsets.UTF_8.name()));
     }
-    return new RestResponse(getClient().execute(post));
+    return execute(post);
   }
 
   public RestResponse delete(String endPoint) throws IOException {
-    HttpDelete delete = new HttpDelete(url + "/a" + endPoint);
-    return new RestResponse(getClient().execute(delete));
+    return execute(Request.Delete(url + "/a" + endPoint));
   }
 
 
diff --git a/lib/httpcomponents/BUCK b/lib/httpcomponents/BUCK
index 8168f97..03669f2 100644
--- a/lib/httpcomponents/BUCK
+++ b/lib/httpcomponents/BUCK
@@ -3,6 +3,15 @@
 VERSION = '4.4.1'
 
 maven_jar(
+  name = 'fluent-hc',
+  id = 'org.apache.httpcomponents:fluent-hc:' + VERSION,
+  bin_sha1 = '96fb842b68a44cc640c661186828b60590c71261',
+  src_sha1 = '702515612b2b94ce3374ed5b579d38cbd308eb4f',
+  license = 'Apache2.0',
+  deps = [':httpclient']
+)
+
+maven_jar(
   name = 'httpclient',
   id = 'org.apache.httpcomponents:httpclient:' + VERSION,
   bin_sha1 = '016d0bc512222f1253ee6b64d389c84e22f697f0',