package com.clxcommunications.xms;

import java.io.Closeable;
import java.io.IOException;
import java.util.concurrent.Future;

import org.apache.http.HttpHost;
import org.apache.http.HttpRequest;
import org.apache.http.HttpResponse;
import org.apache.http.client.methods.HttpUriRequest;
import org.apache.http.concurrent.FutureCallback;
import org.apache.http.impl.nio.client.CloseableHttpAsyncClient;
import org.apache.http.impl.nio.client.HttpAsyncClients;
import org.apache.http.nio.client.HttpAsyncClient;
import org.apache.http.nio.protocol.HttpAsyncRequestProducer;
import org.apache.http.nio.protocol.HttpAsyncResponseConsumer;
import org.apache.http.protocol.HttpContext;

/**
 * The HTTP client used if the user did not provide a custom one. It is a direct
 * wrapper around a "proper" HTTP client and mainly functions as a marker for
 * {@link ApiConnection}.
 */
final class ApiDefaultHttpAsyncClient implements HttpAsyncClient, Closeable {

	/*
	 * TODO: Better default client. Need timeout values, max connections per
	 * route, max overall connections, etc.
	 */
	private final CloseableHttpAsyncClient client;

	public ApiDefaultHttpAsyncClient() {
		client = HttpAsyncClients.createMinimal();
	}

	void start() {
		client.start();
	}

	@Override
	public void close() throws IOException {
		client.close();
	}

	@Override
	public <T> Future<T> execute(HttpAsyncRequestProducer requestProducer,
	        HttpAsyncResponseConsumer<T> responseConsumer, HttpContext context,
	        FutureCallback<T> callback) {
		return client.execute(requestProducer, responseConsumer, context,
		        callback);
	}

	@Override
	public <T> Future<T> execute(HttpAsyncRequestProducer requestProducer,
	        HttpAsyncResponseConsumer<T> responseConsumer,
	        FutureCallback<T> callback) {
		return client.execute(requestProducer, responseConsumer, callback);
	}

	@Override
	public Future<HttpResponse> execute(HttpHost target, HttpRequest request,
	        HttpContext context, FutureCallback<HttpResponse> callback) {
		return client.execute(target, request, context, callback);
	}

	@Override
	public Future<HttpResponse> execute(HttpHost target, HttpRequest request,
	        FutureCallback<HttpResponse> callback) {
		return client.execute(target, request, callback);
	}

	@Override
	public Future<HttpResponse> execute(HttpUriRequest request,
	        HttpContext context, FutureCallback<HttpResponse> callback) {
		return client.execute(request, context, callback);
	}

	@Override
	public Future<HttpResponse> execute(HttpUriRequest request,
	        FutureCallback<HttpResponse> callback) {
		return client.execute(request, callback);
	}

}

@@ -953,257 +953,522 @@
 %0A%09/*
+*
 %0A%09 * T
-ODO: Better default client. Need timeout values, max connections per%0A%09 * route, max overall connections, etc.%0A%09 */%0A%09private final CloseableHttpAsyncClient client;%0A%0A%09public ApiDefaultHttpAsyncClient() %7B%0A%09%09client = HttpAsyncClients.createMinimal
+he default maximum number of simultaneous connections to open towards%0A%09 * the XMS endpoint.%0A%09 */%0A%09private static final int DEFAULT_MAX_CONN = 10;%0A%0A%09/**%0A%09 * The underlying actual HTTP client.%0A%09 */%0A%09private final CloseableHttpAsyncClient client;%0A%0A%09public ApiDefaultHttpAsyncClient() %7B%0A%09%09// TODO: Is this a good default setup?%0A%09%09client = HttpAsyncClients.custom()%0A%09%09        .disableCookieManagement()%0A%09%09        .setMaxConnPerRoute(DEFAULT_MAX_CONN)%0A%09%09        .setMaxConnTotal(DEFAULT_MAX_CONN)%0A%09%09        .build
 ();%0A

Use a fancier underlying default HTTP client