Package net.redhillsoftware.bonza

Source Code of net.redhillsoftware.bonza.Bonza

package net.redhillsoftware.bonza;

import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.net.BindException;
import java.net.URISyntaxException;
import java.net.URL;
import java.security.KeyManagementException;
import java.security.KeyStoreException;
import java.security.NoSuchAlgorithmException;
import java.security.UnrecoverableKeyException;
import java.security.cert.X509Certificate;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.List;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.io.IOUtils;
import org.apache.commons.lang.StringUtils;
import org.apache.http.Header;
import org.apache.http.HttpEntity;
import org.apache.http.HttpResponse;
import org.apache.http.client.HttpClient;
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.methods.HttpRequestBase;
import org.apache.http.client.params.CookiePolicy;
import org.apache.http.client.params.HttpClientParams;
import org.apache.http.conn.scheme.Scheme;
import org.apache.http.conn.ssl.SSLSocketFactory;
import org.apache.http.conn.ssl.TrustStrategy;
import org.apache.http.entity.InputStreamEntity;
import org.apache.http.impl.client.DefaultHttpClient;
import org.apache.http.impl.conn.PoolingClientConnectionManager;
import org.eclipse.jetty.server.Connector;
import org.eclipse.jetty.server.Request;
import org.eclipse.jetty.server.Server;
import org.eclipse.jetty.server.handler.AbstractHandler;
import org.eclipse.jetty.server.nio.SelectChannelConnector;

/**
*  Main class for Bonza.
*
*
*/
public final class Bonza extends AbstractHandler {

    private BonzaConfig m_config;
    private HttpClient m_httpClient = createHttpClient();

    public Bonza(BonzaConfig bonzaConfig) throws UnrecoverableKeyException, NoSuchAlgorithmException, KeyStoreException, KeyManagementException {
        m_config = bonzaConfig;
    }

    private HttpClient createHttpClient() throws NoSuchAlgorithmException, KeyManagementException, KeyStoreException, UnrecoverableKeyException {
        HttpClient httpClient = new DefaultHttpClient(new PoolingClientConnectionManager());
        HttpClientParams.setRedirecting(httpClient.getParams(), false);
        HttpClientParams.setCookiePolicy(httpClient.getParams(), CookiePolicy.IGNORE_COOKIES);

        //trust all ssl.
        SSLSocketFactory sslsf = new SSLSocketFactory(new TrustStrategy() {
            public boolean isTrusted(
                    final X509Certificate[] chain, String authType) throws java.security.cert.CertificateException {
                return true;
            }
        });
        httpClient.getConnectionManager().getSchemeRegistry().register(new Scheme("https", 443, sslsf));
        return httpClient;
    }

    @Override
    public void handle(String target, Request baseRequest, HttpServletRequest request, HttpServletResponse response)
            throws IOException, ServletException {

        String requestURI = getPathAndQuery(request);

        String mappedRequest = m_config.mapRequest(requestURI);
        BonzaConfig.Logger log = m_config.requestStart(request, requestURI, mappedRequest);
        if (mappedRequest == null) {
            log.logResponse(404);
            return404(response);
        } else {
            doProxyRequest(mappedRequest, request, response);
            log.logResponse(response.getStatus());
        }

        response.flushBuffer();
    }

    // Everything after the scheme + server
    private String getPathAndQuery(HttpServletRequest request) {
        String requestURI = request.getRequestURI();
        if (request.getQueryString() != null) {
            requestURI += "?" + request.getQueryString();
        }
        return requestURI;
    }

    private void doProxyRequest(String newRequestURL, HttpServletRequest originalRequest, HttpServletResponse originalResponse) throws IOException {
        if (newRequestURL.startsWith("file:")) {
            proxyToFile(newRequestURL, originalRequest, originalResponse);
        } else {
            proxyToHttp(newRequestURL, originalRequest, originalResponse);
        }
    }

    private void proxyToHttp(String newRequestURL, HttpServletRequest originalRequest, HttpServletResponse originalResponse) throws IOException {
        HttpRequestBase method = createProxyRequest(newRequestURL, originalRequest);
        HttpResponse proxyResponse = m_httpClient.execute(method);
        copyProxyResponse(originalRequest, originalResponse, proxyResponse);
    }

    private void proxyToFile(String newRequestURL, HttpServletRequest originalRequest, HttpServletResponse originalResponse)
            throws IOException {

        URL url = new URL(newRequestURL);
        File f;
        try {
            f = new File(url.toURI());
        } catch (URISyntaxException e) {
            f = new File(url.getPath());
        }

        FileInputStream fis = new FileInputStream(f);
        IOUtils.copy(fis, originalResponse.getOutputStream());

    }

    private HttpRequestBase createProxyRequest(String newRequestURL, HttpServletRequest request) throws IOException {
        HttpRequestBase method;
        if (request.getMethod().equalsIgnoreCase("get")) {
            method = new HttpGet(newRequestURL);
        } else if (request.getMethod().equalsIgnoreCase("put")) {
            HttpPut putMethod = new HttpPut(newRequestURL);
            putMethod.setEntity(new InputStreamEntity(request.getInputStream(), request.getContentLength()));
            method = putMethod;
        } else {
            HttpPost postMethod = new HttpPost(newRequestURL);
            postMethod.setEntity(new InputStreamEntity(request.getInputStream(), request.getContentLength()));
            method = postMethod;
        }
       
        copyHeaders(request, method);

        return method;
    }

    private void copyHeaders(HttpServletRequest request, HttpRequestBase method) {
        for (String headerName : Collections.list(request.getHeaderNames())) {
            for (String headerValue : Collections.list(request.getHeaders(headerName))) {
                if (!"Connection".equals(headerName) && !"Content-Length".equals(headerName)) {
                    method.setHeader(headerName, headerValue);
                }
            }
        }
    }

    private void copyProxyResponse(HttpServletRequest originalRequest,
                                   HttpServletResponse originalResponse,
                                   HttpResponse proxyResponse) throws IOException {
        for (Header header : proxyResponse.getAllHeaders()) {
            String headerName = header.getName();
            String headerValue = header.getValue();
            if (headerName.equals("Location")) {
                headerValue = m_config.reverseMap(headerValue, originalRequest);
            }
            if (headerName.equals("Set-Cookie")) {
                headerValue = crunchCookie(originalRequest, headerValue);
            }
            originalResponse.addHeader(headerName, headerValue);
        }
        int statusCode = proxyResponse.getStatusLine().getStatusCode();
        originalResponse.setStatus(statusCode);
        HttpEntity entity = proxyResponse.getEntity();
        if (entity != null) {
            entity.writeTo(originalResponse.getOutputStream());
        }
    }

    private String crunchCookie(HttpServletRequest originaRequest, String headerValue) {
        if (originaRequest.getRequestURL().toString().startsWith("https")) {
            return headerValue;
        }
        List<String> parts = new ArrayList<String>();
        for (String part : Arrays.asList(headerValue.split("; "))) {
            if (!part.equals("Secure")) {
                parts.add(part);
            }
        }
        return StringUtils.join(parts, "; ");

    }

    /**
     * Return a 404 if we can't map anything.
     */
    private void return404(HttpServletResponse response) throws IOException {
        response.setStatus(404);
        response.getWriter().append("You've got buckley's chance of getting anything on this URL!");
    }

    public static void main(String[] args) throws Exception {

        BonzaConfig config = BonzaConfig.parseOptions(args);

        org.eclipse.jetty.util.log.Log.setLog(null);

        Server server = new Server();

        try {
            SelectChannelConnector connector = new SelectChannelConnector();
            connector.setReuseAddress(false);
            connector.setPort(config.getPort());
            server.setConnectors(new Connector[]{connector});
            server.setHandler(new Bonza(config));
            server.start();
            out("You beauty!! Lets go.");
            out("\n" + config.toString());
            server.join();
        } catch (BindException e) {
            System.exit(1);
        }
    }

    public static void out(String msg) {
        System.out.println(msg);
    }

    public static void err(String emsg) {
        System.err.println(emsg);
    }
}
TOP

Related Classes of net.redhillsoftware.bonza.Bonza

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.