/*******************************************************************************
*
* Copyright (c) 2004-2010 Oracle Corporation.
*
* 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:
*
*
*******************************************************************************/
package org.jvnet.hudson.test;
import hudson.Util;
import hudson.util.IOUtils;
import org.apache.commons.io.FileUtils;
import org.mortbay.jetty.Server;
import org.mortbay.jetty.bio.SocketConnector;
import org.mortbay.jetty.handler.ContextHandlerCollection;
import org.mortbay.jetty.servlet.Context;
import org.mortbay.jetty.servlet.ServletHolder;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.File;
import java.io.IOException;
import java.net.URL;
/**
* Acts as a reverse proxy to https://hudson.java.net/ , so that during a test
* we can avoid hitting java.net.
*
* <p> The contents are cached locally.
*
* @author Kohsuke Kawaguchi
*/
public class JavaNetReverseProxy extends HttpServlet {
private final Server server;
public final int localPort;
private final File cacheFolder;
public JavaNetReverseProxy(File cacheFolder) throws Exception {
this.cacheFolder = cacheFolder;
cacheFolder.mkdirs();
server = new Server();
ContextHandlerCollection contexts = new ContextHandlerCollection();
server.setHandler(contexts);
Context root = new Context(contexts, "/", Context.SESSIONS);
root.addServlet(new ServletHolder(this), "/");
SocketConnector connector = new SocketConnector();
server.addConnector(connector);
server.start();
localPort = connector.getLocalPort();
}
public void stop() throws Exception {
server.stop();
}
// class Response {
// final URL url;
// final String contentType;
// final ByteArrayOutputStream data = new ByteArrayOutputStream();
//
// Response(URL url) throws IOException {
// this.url = url;
// URLConnection con = url.openConnection();
// contentType = con.getContentType();
// IOUtils.copy(con.getInputStream(),data);
// }
//
// void reproduceTo(HttpServletResponse rsp) throws IOException {
// rsp.setContentType(contentType);
// data.writeTo(rsp.getOutputStream());
// }
// }
@Override
protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
String path = req.getServletPath();
String d = Util.getDigestOf(path);
File cache = new File(cacheFolder, d);
if (!cache.exists()) {
URL url = new URL("http://hudson-ci.org/" + path);
FileUtils.copyURLToFile(url, cache);
}
resp.setContentType(getMimeType(path));
IOUtils.copy(cache, resp.getOutputStream());
}
private String getMimeType(String path) {
int idx = path.indexOf('?');
if (idx >= 0) {
path = path.substring(0, idx);
}
if (path.endsWith(".json")) {
return "text/javascript";
}
return getServletContext().getMimeType(path);
}
private static volatile JavaNetReverseProxy INSTANCE;
/**
* Gets the default instance.
*/
public static synchronized JavaNetReverseProxy getInstance() throws Exception {
if (INSTANCE == null) // TODO: think of a better location --- ideally inside the target/ dir so that clean would wipe them out
{
INSTANCE = new JavaNetReverseProxy(new File(new File(System.getProperty("java.io.tmpdir")), "hudson-ci.org-cache2"));
}
return INSTANCE;
}
}