MockServer provides the following types of proxy:

  • Port Forwarding
    • all requests for a specific local port are forwarded to a different (local or remote) port and hostname for the system being proxied
  • Web Proxy (i.e. HTTP proxy)
    • each request is forwarded dynamically using its Host header
  • Secure Web Proxy (i.e. HTTPS tunneling proxying)
    • requests are forwarded using a CONNECT request that setups an HTTP tunnel
    • an SSL certificate is auto-generated allowing encrypted HTTPS traffic to be recorded transparently
  • SOCKS Proxy (i.e. dynamic port forwarding)
    • requests are forwarded using a SOCK CONNECT CMD request that established a socket tunnel
    • if the traffic is encrypted an SSL certificate is auto-generated allowing SSL traffic to be recorded transparently

The port forwarding and the SOCKS proxy are the most transparent and typically don't require any code changes. However the Web Proxy and Secure Web Proxy ensure only configured clients are proxied and that multiple services can be simultaneously proxies.

 

Port Forwarding

Client

Port forwarding is very simple as it does not require any code changes. The port forwarding proxy is configured to send all received requests to remote port and host.

Although the port forwarding proxy is the simplest proxy is can only proxy a single remote port and host. To forward multiple ports, multiple port forwarding proxies, should be run as separate processes.

There are two many approaches for routing requests via the port forwarding proxy.

  1. Update the remote service host and port used by the client, typically this is either hard coded or in a configuration file. Change the remote service host and port to the host and port where the proxy is running.
  2. Add entry to the /etc/hosts file to map one or more remote domain names to the machine where the proxy is running. This approach will not require any configuration file changes as the operating system will resolve the remote domain name to maching where the proxy is running. However, this approach will only work if it is possible to start MockServer locally on the same port the client is connecting to on the remote machine.

Proxy

To run the Port Forwarding Proxy the following values need to be provided to MockServer:

  • serverPort - specifies the HTTP and HTTPS port for the MockServer.
  • proxyRemotePort - specifies the port to forward all proxy requests to.
  • proxyRemoteHost - specified the host to forward all proxy requests to as a domain name or ip address. If no value is provided when proxyRemotePort has been specified, the default "localhost" is used.

For details of how to run MockServer with the above values configured see Running MockServer

 

Web Proxy & Secure Web Proxy

Client

To use the Web Proxy and Secure Web Proxy HTTP clients must be configured correctly.

Example code or screen-shots is shown below explaining how to configure the following clients:

Proxy

To run the Web Proxy or Secure Web Proxy the following values need to be provided to MockServer:

  • serverPort - specifies the HTTP and HTTPS port for the MockServer.

For details of how to run MockServer with the above values configured see Running MockServer

 

Java JDK HttpURLConnection (HTTP)

Configure the Web or Secure Web Proxy with an HttpURLConnection from the Java JDK, as follows:

private HttpURLConnection sendRequestViaProxy(URL url) throws IOException {
    Proxy proxy = new Proxy(Proxy.Type.HTTP, new InetSocketAddress(System.getProperty("http.proxyHost"), Integer.parseInt(System.getProperty("http.proxyPort"))));
    return (HttpURLConnection) url.openConnection(proxy);
}
 

Apache HttpClient (HTTP)

Configure the Web or Secure Web Proxy with an Apache HttpClient, as follows:

HttpHost httpHost = new HttpHost(System.getProperty("http.proxyHost"), Integer.parseInt(System.getProperty("http.proxyPort")));
DefaultProxyRoutePlanner defaultProxyRoutePlanner = new DefaultProxyRoutePlanner(httpHost);
HttpClient httpClient = HttpClients.custom().setRoutePlanner(defaultProxyRoutePlanner).build();

The mockserver-example project contains an example of using the Web Proxy (i.e. HTTP Proxy) with a Apache HttpClient called BookServiceApacheHttpClient that demonstrates a fully working example.

 

Spring RestTemplate

Configure the Web or Secure Web Proxy with a Spring RestTemplate, as follows:

RestTemplate restTemplate = new RestTemplate();
HttpHost httpHost = new HttpHost(
        System.getProperty("http.proxyHost"),
        Integer.parseInt(System.getProperty("http.proxyPort"))
);
DefaultProxyRoutePlanner defaultProxyRoutePlanner = new DefaultProxyRoutePlanner(httpHost);
HttpClient httpClient = HttpClients.custom().setRoutePlanner(defaultProxyRoutePlanner).build();
restTemplate.setRequestFactory(new HttpComponentsClientHttpRequestFactory(httpClient));

The mockserver-example project contains an example of using the Web Proxy (i.e. HTTP Proxy) with a Spring RestTemplate called BookServiceSpringRestTemplateClient that demonstrates a fully working example.

 

Google Client (HTTP)

Configure the Web or Secure Web Proxy with a Google HTTP Client, as follows:

private HttpResponse sendRequestViaProxy(URL url, String method, @Nullable HttpContent content) throws IOException {
    ProxySelector defaultProxySelector = ProxySelector.getDefault();
    try {
        ProxySelector.setDefault(new ProxySelector() {
            @Override
            public List<Proxy> select(URI uri) {
                return Arrays.asList(new Proxy(Proxy.Type.HTTP, new InetSocketAddress(System.getProperty("http.proxyHost"), Integer.parseInt(System.getProperty("http.proxyPort")))));
            }

            @Override
            public void connectFailed(URI uri, SocketAddress sa, IOException ioe) {
                System.out.println("Connection could not be established to proxy at socket [" + sa + "]");
                ioe.printStackTrace();
            }
        });
        HttpRequestFactory requestFactory = new NetHttpTransport().createRequestFactory();
        return requestFactory.buildRequest(method, new GenericUrl(url), content).execute();
    } finally {
        ProxySelector.setDefault(defaultProxySelector);
    }
}
 

Jetty HttpClient

Configure the Web or Secure Web Proxy with a Jetty HttpClient, as follows:

Jetty HttpClient 9.x

HttpClient httpClient = new HttpClient();
try {
    httpClient.getProxyConfiguration().getProxies().add(new HttpProxy(System.getProperty("http.proxyHost"), Integer.parseInt(System.getProperty("http.proxyPort"));
    httpClient.start();
} catch (Exception e) {
    throw new RuntimeException("Exception creating HttpClient", e);
}

Jetty HttpClient 8.x

HttpClient httpClient = new HttpClient();
try {
    httpClient.setProxy(new Address(System.getProperty("http.proxyHost"), Integer.parseInt(System.getProperty("http.proxyPort"));
    httpClient.start();
} catch (Exception e) {
    throw new RuntimeException("Exception creating HttpClient", e);
}

The mockserver-example project contains an example of using the Web Proxy (i.e. HTTP Proxy) with a Jetty HttpClient called BookServiceJettyHttpClient that demonstrates a fully working example.

 

Jersey Client

Configure the Web or Secure Web Proxy with a Jersey Client, as follows:

ClientConfig clientConfig = new ClientConfig().register(new JacksonFeature())
                                              .connectorProvider(new ApacheConnectorProvider());
clientConfig.property(ClientProperties.PROXY_URI, "http://" + System.getProperty("http.proxyHost") + ":" + System.getProperty("http.proxyPort"));
Client client = ClientBuilder.newClient(clientConfig);

The mockserver-example project contains an example of using the Web Proxy (i.e. HTTP Proxy) with a Jersey Client called BookServiceJerseyClient that demonstrates a fully working example.

 

Grizzly AsyncHttpClient

Configure the Web or Secure Web Proxy with a Grizzly AsyncHttpClient, as follows:

AsyncHttpClientConfig.Builder clientConfigBuilder = new AsyncHttpClientConfig.Builder();
clientConfigBuilder.setProxyServerSelector(ProxyUtils.createProxyServerSelector(HttpProxy.proxySelector()));
AsyncHttpClient asyncHttpClient = new AsyncHttpClient(clientConfigBuilder.build());

The mockserver-example project contains an example of using the Web Proxy (i.e. HTTP Proxy) with a Grizzly AsyncHttpClient called BookServiceGrizzlyHttpClient that demonstrates a fully working example.

 

Apple Mac HTTP & HTTPS (i.e. Chrome, Safari, Firefox, etc)

The Apple Mac can be configure to send all HTTP or HTTPS request via a proxy. This is done in the proxy settings in System Preferences > Network > Advanced > Proxies, as follows:

1. System Preferences

Apple Mac System Preferences

2. Network Preferences

Apple Mac Network Preferences

3. Web Proxy Settings (HTTP requests)

Web Proxy Configuration

4. Secure Web Proxy Settings (HTTPS requests)

Secure Web Proxy Configuration

 

SOCKS Proxy

Client

The SOCKS Proxy operates at the socket level, therefore, it is possible to configure a single client, an entire JVM or an entire operating system to send all network requests via the SOCKS Proxy.

Example code or screen-shots is shown below explaining how to configure the following clients:

Proxy

To run the SOCKS Proxy the following values need to be provided to MockServer:

  • serverPort - specifies the SOCKS port for the MockServer.

For details of how to run MockServer with the above values configured see Running MockServer

 

Apache HttpClient (SOCKS)

Configure the SOCKS Proxy with an Apache HttpClient, as follows:

Registry<ConnectionSocketFactory> socketFactoryRegistry = RegistryBuilder.<ConnectionSocketFactory>create()
        .register("http", new ConnectionSocketFactory() {

            public Socket createSocket(final HttpContext context) throws IOException {
                return new Socket(
                        java.net.Proxy.Type.SOCKS,
                        new InetSocketAddress(
                                System.getProperty("http.proxyHost"),
                                Integer.parseInt(System.getProperty("http.proxyPort"))
                        )));
            }

            public Socket connectSocket(
                    final int connectTimeout,
                    final Socket socket,
                    final HttpHost host,
                    final InetSocketAddress remoteAddress,
                    final InetSocketAddress localAddress,
                    final HttpContext context) throws IOException {
                Socket sock;
                if (socket != null) {
                    sock = socket;
                } else {
                    sock = createSocket(context);
                }
                if (localAddress != null) {
                    sock.bind(localAddress);
                }
                try {
                    sock.connect(remoteAddress, connectTimeout);
                } catch (SocketTimeoutException ex) {
                    throw new ConnectTimeoutException(ex, host, remoteAddress.getAddress());
                }
                return sock;
            }

        })
        .build();

PoolingHttpClientConnectionManager clientConnectionManager = new PoolingHttpClientConnectionManager(socketFactoryRegistry);
HttpClient httpClient = HttpClients.custom()
        .setConnectionManager(clientConnectionManager)
        .build();
 

Java JDK HttpURLConnection (SOCKS)

Configure the SOCKS Proxy with an HttpURLConnection from the Java JDK, as follows:

private HttpURLConnection sendRequestViaProxy(URL url) throws IOException {
    Proxy proxy = new Proxy(Proxy.Type.SOCKS, new InetSocketAddress(System.getProperty("http.proxyHost"), Integer.parseInt(System.getProperty("http.proxyPort"))));
    return (HttpURLConnection) url.openConnection(proxy);
}

The mockserver-example project contains an example of using the SOCKS Proxy with a HttpURLConnection called BookServiceJavaHttpClient that demonstrates a fully working example.

 

Google HTTP Client (SOCKS)

Configure the SOCKS Proxy with a Google HTTP Client, as follows:

private HttpResponse sendRequestViaProxy(URL url, String method, @Nullable HttpContent content) throws IOException {
    ProxySelector defaultProxySelector = ProxySelector.getDefault();
    try {
        ProxySelector.setDefault(new ProxySelector() {
            @Override
            public List<Proxy> select(URI uri) {
                return Arrays.asList(new Proxy(Proxy.Type.SOCKS, new InetSocketAddress(System.getProperty("http.proxyHost"), Integer.parseInt(System.getProperty("http.proxyPort")))));
            }

            @Override
            public void connectFailed(URI uri, SocketAddress sa, IOException ioe) {
                System.out.println("Connection could not be established to proxy at socket [" + sa + "]");
                ioe.printStackTrace();
            }
        });
        HttpRequestFactory requestFactory = new NetHttpTransport().createRequestFactory();
        return requestFactory.buildRequest(method, new GenericUrl(url), content).execute();
    } finally {
        ProxySelector.setDefault(defaultProxySelector);
    }
}

The mockserver-example project contains an example of using the SOCKS Proxy with a Google HTTP Client called BookServiceGoogleHttpClient that demonstrates a fully working example.

 

JVM Configuration

It is possible to enable the SOCK proxy for the entire JVM, as follows:

ProxySelector.setDefault(new ProxySelector() {
    @Override
    public List<java.net.Proxy> select(URI uri) {
        return Arrays.asList(
                new java.net.Proxy(
                            java.net.Proxy.Type.SOCKS,
                        new InetSocketAddress(
                                System.getProperty("http.proxyHost"),
                                Integer.parseInt(System.getProperty("http.proxyPort"))
                        )
                )
        );
    }

    @Override
    public void connectFailed(URI uri, SocketAddress sa, IOException ioe) {
        logger.error("Connection could not be established to proxy at socket [" + sa + "]", ioe);
    }
});
 

Apple Mac Network Stack (SOCKS)

The Apple Mac can be configure to send all network requests via a SOCKS proxy. This is done in the proxy settings in System Preferences > Network > Advanced > Proxies, as follows:

1. System Preferences

Apple Mac System Preferences

2. Network Preferences

Apple Mac Network Preferences

3. SOCKS Proxy Settings

SOCKS Proxy Configuration