| /******************************************************************************* | |
| * Copyright (c) 2007, 2008 IBM Corporation and Others | |
| * All rights reserved. This program and the accompanying materials | |
| * are made available under the terms of the Eclipse Public License v1.0 | |
| * which accompanies this distribution, and is available at | |
| * http://www.eclipse.org/legal/epl-v10.html | |
| * | |
| * Contributors: | |
| * Hisashi MIYASHITA - initial API and implementation | |
| * Kentarou FUKUDA - initial API and implementation | |
| *******************************************************************************/ | |
| package org.eclipse.actf.util.internal.httpproxy; | |
| import java.io.IOException; | |
| import java.net.InetSocketAddress; | |
| import java.net.ServerSocket; | |
| import java.net.Socket; | |
| import java.net.SocketAddress; | |
| import java.net.SocketException; | |
| import org.eclipse.actf.util.httpproxy.ExternalProxyConfig; | |
| import org.eclipse.actf.util.httpproxy.IHTTPProxy; | |
| import org.eclipse.actf.util.httpproxy.ProxyConfig; | |
| import org.eclipse.actf.util.httpproxy.core.IClientConnection; | |
| import org.eclipse.actf.util.httpproxy.proxy.IHTTPLocalServerFactory; | |
| import org.eclipse.actf.util.httpproxy.proxy.IHTTPProxyConnection; | |
| import org.eclipse.actf.util.httpproxy.proxy.IHTTPProxyTranscoderFactory; | |
| import org.eclipse.actf.util.httpproxy.proxy.IHTTPSessionOverriderFactory; | |
| import org.eclipse.actf.util.httpproxy.proxy.ISecretManager; | |
| import org.eclipse.actf.util.httpproxy.util.Logger; | |
| import org.eclipse.actf.util.internal.httpproxy.core.ClientConnectionListener; | |
| import org.eclipse.actf.util.internal.httpproxy.proxy.ClientStateManager; | |
| import org.eclipse.actf.util.internal.httpproxy.proxy.HTTPProxyConnection; | |
| /** | |
| * HTTPProxy is the class for the server instance of HTTP proxy. | |
| */ | |
| public class HTTPProxy implements ClientConnectionListener, IHTTPProxy { | |
| private static final Logger LOGGER = Logger.getLogger(HTTPProxy.class); | |
| private final IWorkpileController wpc; | |
| private final ServerSocket fServerSock; | |
| private final long fKeepAlive; | |
| private final int fQueueSize; | |
| // private final AsyncWorkManager fDispatchWorkMan; | |
| private final IObjectPool connectionPool; | |
| private final ISecretManager secretManager; | |
| private final IHTTPSessionOverriderFactory sessionOverriderFactory; | |
| private final IHTTPProxyTranscoderFactory proxyTranscoderFactory; | |
| private final IHTTPLocalServerFactory localServerFactory; | |
| private ExternalProxyConfig externalProxyConfig; | |
| /** | |
| * | |
| * @return | |
| */ | |
| public ISecretManager getSecretManager() { | |
| return secretManager; | |
| } | |
| /* | |
| * (non-Javadoc) | |
| * | |
| * @see org.eclipse.actf.util.httpproxy.IHTTPProxy#getListenPort() | |
| */ | |
| public int getListenPort() { | |
| return fServerSock.getLocalPort(); | |
| } | |
| /** | |
| * @return | |
| */ | |
| public ExternalProxyConfig getExternalProxyConfig() { | |
| return externalProxyConfig; | |
| } | |
| /** | |
| * @return | |
| */ | |
| public IHTTPSessionOverriderFactory getSessionOverriderFactory() { | |
| return sessionOverriderFactory; | |
| } | |
| /** | |
| * @return | |
| */ | |
| public IHTTPProxyTranscoderFactory getProxyTranscoderFactory() { | |
| return proxyTranscoderFactory; | |
| } | |
| /** | |
| * @return | |
| */ | |
| public IHTTPLocalServerFactory getLocalServerFactory() { | |
| return localServerFactory; | |
| } | |
| @SuppressWarnings("nls") | |
| public HTTPProxy(ProxyConfig config, ExternalProxyConfig externalProxyConfig) | |
| throws IOException { | |
| Logger.setConfigPropertyName("WaXcoding.conf.logging"); | |
| this.externalProxyConfig = externalProxyConfig; | |
| wpc = new WorkpileControllerImpl("WaXcoding"); | |
| fServerSock = new ServerSocket(); | |
| SocketAddress sa = new InetSocketAddress("localhost", config.getPort()); | |
| // SocketAddress sa = new InetSocketAddress(localPort); | |
| fServerSock.bind(sa); | |
| fKeepAlive = config.getKeepAliveInterval(); | |
| fQueueSize = config.getMaxQueueSize(); | |
| connectionPool = new ObjectPoolImpl("WaXcoding-clientconnections"); | |
| for (int i = 0; i < config.getMaxConnection(); i++) { | |
| IHTTPProxyConnection obj = new HTTPProxyConnection(this, | |
| fQueueSize, config.getTimeout()); | |
| connectionPool.add(obj); | |
| } | |
| secretManager = config.getSecretManager(); | |
| sessionOverriderFactory = config.getSessionOverriderFactory(); | |
| proxyTranscoderFactory = config.getProxyTranscoderFactory(); | |
| localServerFactory = config.getLocalServerFactory(); | |
| } | |
| /* | |
| * (non-Javadoc) | |
| * | |
| * @see | |
| * org.eclipse.actf.util.httpproxy.IHTTPProxy#getSecret(java.lang.String, | |
| * boolean) | |
| */ | |
| public String getSecret(String id, boolean remove) { | |
| if (null == secretManager) { | |
| return null; | |
| } | |
| return secretManager.getSecret(id, remove); | |
| } | |
| public synchronized int getCurrentServerGroupIndex() { | |
| return 0; | |
| } | |
| public void connectionClosed(IClientConnection obj) { | |
| connectionPool.add(obj); | |
| } | |
| private boolean exit = false; | |
| @SuppressWarnings("nls") | |
| private void startProxy() { | |
| LOGGER.info("Started WaXcoding, Listening port " | |
| + fServerSock.getLocalPort()); | |
| while (true) { | |
| Socket sock = null; | |
| try { | |
| HTTPProxyConnection connection = (HTTPProxyConnection) connectionPool | |
| .take(0); | |
| sock = fServerSock.accept(); | |
| sock.setSoTimeout(1); | |
| if (exit) | |
| break; | |
| // if (sock != null) { | |
| connection.init(ClientStateManager.getClientStateManager(this), | |
| sock, fKeepAlive, getCurrentServerGroupIndex()); | |
| wpc.input(connection); | |
| // } | |
| } catch (InterruptedException e) { | |
| if (exit) { | |
| LOGGER.info("Stopping WaXcoding..."); | |
| break; | |
| } | |
| } catch (SocketException e) { | |
| // this exception is thrown when the socket is closed. | |
| } catch (Exception e) { | |
| e.printStackTrace(); | |
| System.out.println(wpc.toString()); | |
| } | |
| } | |
| } | |
| private void cleanup() { | |
| LOGGER.info("...done"); //$NON-NLS-1$ | |
| } | |
| private class ProxyThread extends Thread { | |
| private boolean threadExit; | |
| public void exit() { | |
| exit = true; | |
| synchronized (this) { | |
| while (!threadExit) { | |
| this.interrupt(); | |
| try { | |
| fServerSock.close(); | |
| wait(1000); | |
| } catch (IOException e) { | |
| } catch (InterruptedException e) { | |
| e.printStackTrace(); | |
| } | |
| } | |
| } | |
| } | |
| public void run() { | |
| startProxy(); | |
| cleanup(); | |
| synchronized (this) { | |
| threadExit = true; | |
| notifyAll(); | |
| } | |
| } | |
| ProxyThread() { | |
| super("ProxyThread"); //$NON-NLS-1$ | |
| threadExit = false; | |
| } | |
| } | |
| private ProxyThread proxyThread; | |
| /* | |
| * (non-Javadoc) | |
| * | |
| * @see org.eclipse.actf.util.httpproxy.IHTTPProxy#startThread() | |
| */ | |
| public void startThread() { | |
| if (proxyThread != null) | |
| return; | |
| proxyThread = new ProxyThread(); | |
| proxyThread.start(); | |
| } | |
| /* | |
| * (non-Javadoc) | |
| * | |
| * @see org.eclipse.actf.util.httpproxy.IHTTPProxy#stopThread() | |
| */ | |
| public void stopThread() { | |
| proxyThread.exit(); | |
| proxyThread = null; | |
| } | |
| private static final String USAGE_PARAMS = " <localport>"; //$NON-NLS-1$ | |
| private static void PRINT_USAGE(String msg) { | |
| if (msg != null && msg.length() > 0) { | |
| System.err.println(msg); | |
| } | |
| System.err.println("Usage: java " + HTTPProxy.class.getName() //$NON-NLS-1$ | |
| + USAGE_PARAMS); | |
| } | |
| /** | |
| * A sample bootstrap code for stand-alone HTTP proxy process. | |
| * | |
| * @param args | |
| */ | |
| public static void main(String[] args) { | |
| if (args.length < 1) { | |
| PRINT_USAGE(null); | |
| System.exit(1); | |
| } | |
| int argsOffset = 0; | |
| int localport = Integer.parseInt(args[argsOffset++]); | |
| ProxyConfig config = new ProxyConfig(); | |
| ExternalProxyConfig externalProxyConfig = new ExternalProxyConfig(); | |
| try { | |
| Logger.configure(); | |
| } catch (Exception e) { | |
| e.printStackTrace(); | |
| // System.exit(1); | |
| } | |
| try { | |
| HTTPProxy proxy = new HTTPProxy(config, externalProxyConfig); | |
| proxy.startProxy(); | |
| } catch (IOException e) { | |
| System.err.println("Port is in use: " + localport); //$NON-NLS-1$ | |
| System.exit(1); | |
| } | |
| } | |
| } |