Search in sources :

Example 1 with HttpClientRequest

use of org.vertx.java.core.http.HttpClientRequest in project fabric8 by jboss-fuse.

the class HttpGatewayHandler method doRouteRequest.

protected void doRouteRequest(Map<String, MappedServices> mappingRules, final HttpServerRequest request) {
    String uri = request.uri();
    String uri2 = uri;
    if (addMissingTrailingSlashes) {
        uri2 = normalizeUri(uri);
    }
    HttpClient client = null;
    String remaining = null;
    String prefix = null;
    String proxyServiceUrl = null;
    String reverseServiceUrl = null;
    MappedServices mappedServices = null;
    URL clientURL = null;
    Set<Map.Entry<String, MappedServices>> entries = mappingRules.entrySet();
    for (Map.Entry<String, MappedServices> entry : entries) {
        String path = entry.getKey();
        mappedServices = entry.getValue();
        String pathPrefix = path;
        boolean uriMatches = uri.startsWith(pathPrefix);
        boolean uri2Matches = uri2 != null && uri2.startsWith(pathPrefix);
        if (uriMatches || uri2Matches) {
            int pathPrefixLength = pathPrefix.length();
            if (uri2Matches && pathPrefixLength < uri2.length()) {
                remaining = uri2.substring(pathPrefixLength);
            } else if (pathPrefixLength < uri.length()) {
                remaining = uri.substring(pathPrefixLength);
            } else {
                remaining = null;
            }
            // now lets pick a service for this path
            proxyServiceUrl = mappedServices.chooseService(request);
            if (proxyServiceUrl != null) {
                // lets create a client for this request...
                try {
                    clientURL = new URL(proxyServiceUrl);
                    client = createClient(clientURL);
                    prefix = clientURL.getPath();
                    reverseServiceUrl = request.absoluteURI().resolve(pathPrefix).toString();
                    if (reverseServiceUrl.endsWith("/")) {
                        reverseServiceUrl = reverseServiceUrl.substring(0, reverseServiceUrl.length() - 1);
                    }
                    break;
                } catch (MalformedURLException e) {
                    LOG.warn("Failed to parse URL: " + proxyServiceUrl + ". " + e, e);
                }
            }
        }
    }
    if (client != null) {
        String servicePath = prefix != null ? prefix : "";
        // we should usually end the prefix path with a slash for web apps at least
        if (servicePath.length() > 0 && !servicePath.endsWith("/")) {
            servicePath += "/";
        }
        if (remaining != null) {
            servicePath += remaining;
        }
        client.exceptionHandler(new Handler<Throwable>() {

            @Override
            public void handle(Throwable throwable) {
                if (throwable instanceof ConnectTimeoutException) {
                    request.response().setStatusCode(504);
                    request.response().end();
                } else {
                    LOG.error("Unhandled exception", throwable);
                }
            }
        });
        client.setConnectTimeout(connectionTimeout);
        LOG.info("Proxying request {} to service path: {} on service: {} reverseServiceUrl: {}", uri, servicePath, proxyServiceUrl, reverseServiceUrl);
        final HttpClient finalClient = client;
        Handler<HttpClientResponse> responseHandler = new Handler<HttpClientResponse>() {

            public void handle(HttpClientResponse clientResponse) {
                LOG.debug("Proxying response: {}", clientResponse.statusCode());
                request.response().setStatusCode(clientResponse.statusCode());
                request.response().headers().set(clientResponse.headers());
                applyChunkedEncoding(request.response());
                clientResponse.dataHandler(new Handler<Buffer>() {

                    public void handle(Buffer data) {
                        LOG.debug("Proxying response body: {}", data);
                        request.response().write(data);
                    }
                });
                clientResponse.endHandler(new VoidHandler() {

                    public void handle() {
                        request.response().end();
                        finalClient.close();
                    }
                });
            }
        };
        if (mappedServices != null) {
            ProxyMappingDetails proxyMappingDetails = new ProxyMappingDetails(proxyServiceUrl, reverseServiceUrl, servicePath);
            responseHandler = mappedServices.wrapResponseHandlerInPolicies(request, responseHandler, proxyMappingDetails);
        }
        final HttpClientRequest clientRequest = client.request(request.method(), servicePath, responseHandler);
        clientRequest.headers().set(request.headers());
        clientRequest.setChunked(true);
        if (requestTimeout != DEFAULT_REQUEST_TIMEOUT) {
            clientRequest.exceptionHandler(new Handler<Throwable>() {

                @Override
                public void handle(Throwable throwable) {
                    if (throwable instanceof TimeoutException) {
                        request.response().setStatusCode(504);
                        request.response().end();
                    } else {
                        LOG.error("Unhandled exception", throwable);
                    }
                }
            });
            clientRequest.setTimeout(requestTimeout);
        }
        request.dataHandler(new Handler<Buffer>() {

            public void handle(Buffer data) {
                LOG.debug("Proxying request body: {}", data);
                clientRequest.write(data);
            }
        });
        request.endHandler(new VoidHandler() {

            public void handle() {
                LOG.debug("end of the request");
                clientRequest.end();
            }
        });
    } else {
        // lets return a 404
        LOG.info("Could not find matching proxy path for {} from paths: {}", uri, mappingRules.keySet());
        request.response().setStatusCode(404);
        request.response().end();
    }
}
Also used : Buffer(org.vertx.java.core.buffer.Buffer) VoidHandler(org.vertx.java.core.VoidHandler) MalformedURLException(java.net.MalformedURLException) VoidHandler(org.vertx.java.core.VoidHandler) Handler(org.vertx.java.core.Handler) URL(java.net.URL) HttpClientRequest(org.vertx.java.core.http.HttpClientRequest) HttpClient(org.vertx.java.core.http.HttpClient) HttpClientResponse(org.vertx.java.core.http.HttpClientResponse) HashMap(java.util.HashMap) Map(java.util.Map) ConnectTimeoutException(io.netty.channel.ConnectTimeoutException) TimeoutException(java.util.concurrent.TimeoutException) ConnectTimeoutException(io.netty.channel.ConnectTimeoutException)

Aggregations

ConnectTimeoutException (io.netty.channel.ConnectTimeoutException)1 MalformedURLException (java.net.MalformedURLException)1 URL (java.net.URL)1 HashMap (java.util.HashMap)1 Map (java.util.Map)1 TimeoutException (java.util.concurrent.TimeoutException)1 Handler (org.vertx.java.core.Handler)1 VoidHandler (org.vertx.java.core.VoidHandler)1 Buffer (org.vertx.java.core.buffer.Buffer)1 HttpClient (org.vertx.java.core.http.HttpClient)1 HttpClientRequest (org.vertx.java.core.http.HttpClientRequest)1 HttpClientResponse (org.vertx.java.core.http.HttpClientResponse)1