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

com.chavaillaz.client.common.vertx.AbstractVertxHttpClient Maven / Gradle / Ivy

Go to download

Library for the creation of asynchronous clients supporting multiple HTTP clients

There is a newer version: 2.1.3
Show newest version
package com.chavaillaz.client.common.vertx;

import static com.chavaillaz.client.common.utility.Utils.getCookieHeader;

import java.io.InputStream;
import java.util.concurrent.CompletableFuture;

import com.chavaillaz.client.common.AbstractHttpClient;
import com.chavaillaz.client.common.security.Authentication;
import com.fasterxml.jackson.databind.JavaType;
import io.vertx.core.Future;
import io.vertx.core.buffer.Buffer;
import io.vertx.core.http.HttpMethod;
import io.vertx.ext.web.client.HttpRequest;
import io.vertx.ext.web.client.HttpResponse;
import io.vertx.ext.web.client.WebClient;

/**
 * Abstract class implementing common parts for Vert.x HTTP.
 */
public abstract class AbstractVertxHttpClient extends AbstractHttpClient implements AutoCloseable {

    protected final WebClient client;

    /**
     * Creates a new abstract client based on Vert.x HTTP client.
     *
     * @param client         The web client to use
     * @param baseUrl        The base URL of endpoints
     * @param authentication The authentication information
     */
    protected AbstractVertxHttpClient(WebClient client, String baseUrl, Authentication authentication) {
        super(baseUrl, authentication);
        this.client = client;
    }

    /**
     * Creates a request based on the given URL and replaces the parameters in it by the given ones.
     *
     * @param method     The HTTP method for the request to build
     * @param url        The URL with possible parameters in it (using braces)
     * @param parameters The parameters value to replace in the URL (in the right order)
     * @return The request having the URL and authentication set
     */
    protected HttpRequest requestBuilder(HttpMethod method, String url, Object... parameters) {
        var request = client.requestAbs(method, url(url, parameters).toString())
                .putHeader(HEADER_CONTENT_TYPE, HEADER_CONTENT_JSON);
        getAuthentication().fillHeaders(request::putHeader);
        getCookieHeader(getAuthentication()).ifPresent(value -> request.putHeader(HEADER_COOKIE, value));
        return request;
    }

    /**
     * Creates a body buffer containing the given object serialized as JSON.
     *
     * @param object The object to serialize
     * @return The corresponding buffer for the request
     */
    protected Buffer body(Object object) {
        return Buffer.buffer(serialize(object));
    }

    /**
     * Handles the request sent and returns a domain object.
     *
     * @param future     The future response
     * @param returnType The domain object type class
     * @param         The domain object type
     * @return A {@link CompletableFuture} with the deserialized domain object
     */
    protected  CompletableFuture handleAsync(Future> future, Class returnType) {
        return handleAsync(future, objectMapper.constructType(returnType));
    }

    /**
     * Handles the request sent and returns a domain object.
     *
     * @param future     The future response
     * @param returnType The domain object type class
     * @param         The domain object type
     * @return A {@link CompletableFuture} with the deserialized domain object
     */
    protected  CompletableFuture handleAsync(Future> future, JavaType returnType) {
        return handleAsyncBase(future)
                .thenApply(HttpResponse::bodyAsString)
                .thenApply(body -> deserialize(body, returnType));
    }

    /**
     * Handles the request sent and returns an input stream.
     *
     * @param future The future response
     * @return A {@link CompletableFuture} with the input stream
     */
    protected CompletableFuture handleAsync(Future> future) {
        return handleAsyncBase(future)
                .thenApply(HttpResponse::body)
                .thenApply(VertxInputStream::new);
    }

    /**
     * Handles the request sent and returns the corresponding response buffer.
     *
     * @param future The future response
     * @return A {@link CompletableFuture} with the response buffer
     */
    protected CompletableFuture> handleAsyncBase(Future> future) {
        CompletableFuture> completableFuture = new CompletableFuture<>();
        future.onSuccess(response -> handleResponse(response, completableFuture))
                .onFailure(completableFuture::completeExceptionally);
        return completableFuture;
    }

    /**
     * Handles the response by transmitting its state to the given {@link CompletableFuture}.
     *
     * @param response          The HTTP response
     * @param completableFuture The completable future to update
     */
    protected void handleResponse(HttpResponse response, CompletableFuture> completableFuture) {
        if (response.statusCode() >= 400) {
            completableFuture.completeExceptionally(responseException(response.statusCode(), response.bodyAsString()));
        } else {
            completableFuture.complete(response);
        }
    }

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

}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy