Skip to content

Instantly share code, notes, and snippets.

@feltnerm
Created October 10, 2012 17:25
Show Gist options
  • Save feltnerm/3867073 to your computer and use it in GitHub Desktop.
Save feltnerm/3867073 to your computer and use it in GitHub Desktop.
Webserver for CS3830
import java.io.*;
import java.net.*;
import java.util.*;
/**
* Primitive HTTP Web Server
* @author Mark Feltner
*
*/
class HttpRequest extends Thread {
private Socket sock;
private PrintWriter server_thread_log;
private static final String LOG_FILE = "P3.LOG";
private final static String CRLF = "\r\n";
/**
* Processes an HTTP request and returns a response.
* @param inSock The incoming client request socket.
*/
public HttpRequest(Socket inSock) {
this.sock = inSock;
try {
this.server_thread_log = new PrintWriter(
new FileWriter(LOG_FILE, true), true);
} catch (IOException e) {
System.err.println("Error reading logfile. Using stdout instead");
this.server_thread_log = new PrintWriter(System.out);
}
}
/**
* Runs the Thread.
*/
public void run() {
try {
this.processRequest();
} catch (Exception e) {
this.log("Error processing request.");
e.printStackTrace();
}
this.server_thread_log.close();
}
/**
* Process an HTTP Request and return a response.
* @throws Exception
*/
private void processRequest() throws Exception {
InputStream socketInput = this.sock.getInputStream();
DataOutputStream clientWriter = new DataOutputStream(
this.sock.getOutputStream());
BufferedReader clientReader = new BufferedReader(
new InputStreamReader(this.sock.getInputStream()));
String requestLine = clientReader.readLine();
String headerLine = clientReader.readLine();
while (!headerLine.equals(""))
{
System.out.println(headerLine);
headerLine = clientReader.readLine();
}
String fileName = parseRequestLine(requestLine);
File responseFile = new File(fileName);
String responseStatus = null;
String responseContentType = null;
String responseBody = null;
if (responseFile.exists())
{
responseStatus = "HTTP/1.1 200 OK";
responseContentType = "Content-type: " + contentType(fileName) + CRLF;
} else
{
responseStatus = "HTTP/1.1 404 Not Found";
responseContentType = "Content-type: text/html" + CRLF;
responseBody = "<HTML>"+
"<HEAD><TITLE>Not Found</TITLE></HEAD>"+
"<BODY>Not Found</BODY></HTML>";
}
clientWriter.writeBytes(responseStatus + CRLF);
clientWriter.writeBytes(responseContentType + CRLF);
clientWriter.writeBytes(CRLF);
if (responseFile.exists() && responseFile.isFile())
{
FileInputStream istream = new FileInputStream(responseFile);
sendBytes(istream, clientWriter);
}
else
{
clientWriter.writeBytes(responseBody);
}
clientWriter.writeBytes(CRLF);
clientWriter.close();
clientReader.close();
socketInput.close();
this.log("Request: " + requestLine);
this.log("Response: " + responseStatus);
}
/**
* Parse the filename requested from the request header.
* @param requestLine The request line header
* @return A file.
*/
private String parseRequestLine(String requestLine) {
return "." + requestLine.split(" ")[1];
}
/**
* Returns a MIMETYPE for a filename
* @param filename Filename with extension
* @return That filename's mimetype.
*/
private String contentType(String filename) {
if (filename.endsWith(".html") || filename.endsWith(".htm"))
{
return "text/html";
}
else if (filename.endsWith(".gif"))
{
return "image/gif";
}
else if (filename.endsWith(".jpg") || filename.endsWith(".jpeg")) {
return "image/jpeg";
}
else
{
return "application/octet-stream";
}
}
/**
* Writes a file to an outputstream
* @param istream The file input stream to read
* @param ostream The outputstream to write to
* @throws Exception
*/
private void sendBytes(FileInputStream istream, OutputStream ostream)
throws Exception
{
byte[] buffer = new byte[1024];
int bytes = 0;
bytes = istream.read(buffer);
while (bytes != -1)
{
ostream.write(buffer);
bytes = istream.read(buffer);
}
this.log("Bytes transferred: " + bytes);
}
/**
* Log a message to the log.
* @param message the message to write.
*/
private void log(String message) {
String client_ip = this.sock.getInetAddress().toString();
int client_port = this.sock.getPort();
String time_now = new Date().toString();
this.server_thread_log.println(time_now + " [" + client_ip + ":"
+ client_port + "] " + "-- " + message);
}
}
class WebServer {
public static final int LISTEN_PORT = 3333;
ServerSocket serv_sock = null;
PrintWriter server_log;
/**
* A multithreaded WebServer
*/
/**
* Runs the webserver and it begins listening for requests.
*/
public void run() {
try {
this.serv_sock = new ServerSocket(LISTEN_PORT);
} catch (IOException e) {
System.err.println("Unable to start server on port: "
+ LISTEN_PORT + '\n'
+ "(maybe someone's already using it?)");
e.printStackTrace();
}
boolean error = false;
while (!error) {
Socket sock = null;
try {
sock = serv_sock.accept();
HttpRequest request = new HttpRequest(sock);
request.start();
} catch (IOException e) {
System.err.println("Error binding to request with client");
e.printStackTrace();
}
}
try {
this.serv_sock.close();
} catch (IOException e) {
}
}
/**
* Main
*/
public static void main(String[] args) {
System.out.println("Web Server...go!");
WebServer app = new WebServer();
app.run();
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment