import java.io.*;
import java.net.*;
import java.util.*;

/**
 * Tiny HTTPD server.
 * DO NOT DEPLOY AS A REAL SERVER.
 *
 * @author JBY
 * @version 1.0
 */
public class httpd implements Runnable {
  public static final int PORT = 8888;
  public static final String serverID;
  public static final String prefix;
  public static final String specialPrefix;
  public static int gid;
  static {
    gid = 1;
    serverID = "HTTPD demo v1.0, please hack me...";
    prefix = "/Users/yunes/public_html";
    specialPrefix = "/~yunes";
  }
  private int id;
  private Socket s;
  public httpd(Socket s) {
    this.s = s;
    this.id = gid++;
    System.out.println(id+" New connection");
  }
  public void run() {
    try {
      BufferedReader bf = new BufferedReader(new InputStreamReader(s.getInputStream()));
      PrintWriter pw = new PrintWriter(s.getOutputStream());
      main_loop:
      while(true) { // should really be timeout controlled
        Vector<String> request = new Vector<String>();
        do { // request-line + header-lines catching code
          String s = bf.readLine();
          if (s==null) break main_loop;
          if (s.equals("")) break; // end of request block
          request.add(s);
          //        System.out.println(id+">>>>>>>>>>>>>>>"+s);
        } while(true);
        // request de-construction
        StringTokenizer st = new StringTokenizer(request.elementAt(0));
        String method = st.nextToken();
        if (method.equals("GET")) { // GET method response code
          // do some URL rewriting
          String rawURL = st.nextToken();
          String url = rawURL;
          // remove trailing special values
          if (url.indexOf('?')!=-1) url = url.substring(0,url.indexOf('?'));
          // private demo special ~ trick removal
          if (url.startsWith(specialPrefix)) url = url.substring(specialPrefix.length());
          System.out.println(id+">>>>>>>>>>>>>url="+url);
          // add demo special prefix
          url = prefix+url;
          System.out.println(id+">>>>>>>>>>>>>file="+url);
          File f = new File(url);
          if (f.exists()) {
            pw.println("HTTP/1.1 200 OK");
            pw.println("Server: "+serverID);
            pw.println("Content-Length: "+(int)f.length());
            pw.println();
            FileReader fr = new FileReader(f);
            char [] buffer = new char[(int)f.length()];
            fr.read(buffer);
            pw.print(buffer);
          } else {
            System.err.println(id+" "+rawURL+" not found");
            pw.println("HTTP/1.1 404 Not Found");
            String msg = "<html><head><title>404 Not Found</title><body>"+
              rawURL+" not found.</body></html>";
            pw.println("Content-Length: "+msg.length());
            pw.println("Server: "+serverID);
            pw.println();
            pw.print(msg);
          }
        } else { // method not supported here
          System.err.println(id+"Method "+method+" not supported");
          pw.println("HTTP/1.1 405 Method Not Allowed");
          String msg = "<html><head><title>405 Method not allowed</title><body>"+
            method+" actually not supported.</body></html>";
          pw.println("Content-Length: "+msg.length());
          pw.println("Server: "+serverID);
          pw.println();
          pw.print(msg);
        }
        pw.flush();
      }
      bf.close();
      pw.close();
      System.out.println(id+" rip");
    } catch(Exception e) {
      System.err.println(id+"erreur dans le service");
      e.printStackTrace();
    }
  }
  public static void main(String []args) {
    System.out.println("NEVER USE THIS SERVER ON ANY PUBLIC MACHINE, SERIOUS SECURITY HOLES INSIDE");
    try {
      ServerSocket ss = new ServerSocket(PORT);
      while (true) {
        Socket s = ss.accept();
        new Thread(new httpd(s)).start();
      }
    } catch(Exception e) {
      e.printStackTrace();
    }
  }
}