All Downloads are FREE. Search and download functionalities are using the official Maven repository.

io.sphere.sdk.http.NingHttpClientAdapterImpl Maven / Gradle / Ivy

The newest version!
package io.sphere.sdk.http;

import com.ning.http.client.*;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.io.IOException;
import java.nio.charset.StandardCharsets;
import java.util.Optional;
import java.util.concurrent.*;

final class NingHttpClientAdapterImpl extends Base implements NingHttpClientAdapter {
    private static final Logger LOGGER = LoggerFactory.getLogger(NingHttpClientAdapterImpl.class);
    private final AsyncHttpClient asyncHttpClient;
    private final ForkJoinPool threadPool = new ForkJoinPool();

    private NingHttpClientAdapterImpl(final AsyncHttpClient asyncHttpClient) {
        this.asyncHttpClient = asyncHttpClient;
    }

    @Override
    public CompletionStage execute(final HttpRequest httpRequest) {
        if (LOGGER.isDebugEnabled()) {
            LOGGER.debug("executing " + httpRequest);
        }
        final Request request = asNingRequest(httpRequest);
        try {
            final CompletionStage future = wrap(asyncHttpClient.executeRequest(request));
            return future.thenApply((Response response) -> {
                final byte[] responseBodyAsBytes = getResponseBodyAsBytes(response);
                Optional body = responseBodyAsBytes.length > 0 ? Optional.of(responseBodyAsBytes) : Optional.empty();
                final HttpResponse httpResponse = HttpResponse.of(response.getStatusCode(), body, Optional.of(httpRequest), HttpHeaders.of(response.getHeaders()));
                if (LOGGER.isDebugEnabled()) {
                    LOGGER.debug("response " + httpResponse);
                }
                return httpResponse;
            });
        } catch (final IOException e) {
            final CompletableFuture future = new CompletableFuture<>();
            future.completeExceptionally(new HttpException(e));
            return future;
        }
    }

    private byte[] getResponseBodyAsBytes(final Response response) {
        try {
            return response.getResponseBodyAsBytes();
        } catch (IOException e) {
            throw new HttpException(e);
        }
    }

    /* package scope for testing */
     Request asNingRequest(final HttpRequest request) {
        final RequestBuilder builder = new RequestBuilder()
                .setUrl(request.getUrl())
                .setMethod(request.getHttpMethod().toString());

        request.getHeaders().getHeadersAsMap().forEach((name, values) -> values.forEach( value -> builder.addHeader(name, value)));

        request.getBody().ifPresent(body -> {
            if (body instanceof StringHttpRequestBody) {
                final String bodyAsString = ((StringHttpRequestBody) body).getString();
                builder.setBodyEncoding(StandardCharsets.UTF_8.name()).setBody(bodyAsString);
            } else if (body instanceof FileHttpRequestBody) {
                builder.setBody(((FileHttpRequestBody) body).getFile());
            } else if (body instanceof FormUrlEncodedHttpRequestBody) {
                ((FormUrlEncodedHttpRequestBody) body).getData().forEach((name, value) -> builder.addQueryParameter(name, value));
            }
        });
        final Request build = builder.build();
        return build;
    }

    @Override
    public void close() {
        asyncHttpClient.close();
        threadPool.shutdown();
    }

    public static NingHttpClientAdapterImpl of(final AsyncHttpClient asyncHttpClient) {
        return new NingHttpClientAdapterImpl(asyncHttpClient);
    }

    /**
     * Creates a {@link CompletionStage} from a {@link ListenableFuture}.
     * @param listenableFuture the future of the ning library
     * @param executor the executor to run the future in
     * @param  Type of the value that will be returned.
     * @return the Java 8 future implementation
     */
    private static  CompletionStage wrap(final ListenableFuture listenableFuture, final Executor executor) {
        final CompletableFuture result = new CompletableFuture<>();
        final Runnable listener = () -> {
            try {
                final T value = listenableFuture.get();
                result.complete(value);
            } catch (final InterruptedException | ExecutionException e) {
                result.completeExceptionally(e.getCause());
            }
        };
        listenableFuture.addListener(listener, executor);
        return result;
    }

    private CompletionStage wrap(final ListenableFuture listenableFuture) {
        return wrap(listenableFuture, threadPool);
    }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy