This is an old revision of the document!
Saját HTTP szerver mintapélda
Készítsünk egy üres Java projektet, hozzunk létre egy 404.html és egy index.html nevű fájlt az alábbi tartalommal. Majd figyeljük meg hogy a hibakezelés redundáns, azaz kétszer van megírva 404 és 501-es hiba kezelése. Feladat: készítsen egy általános hibakezelő függvényt a hibák kliens oldalra visszadására.
404.html tartalma:
<html> <body> <h1>File not found error</h1> </body> </html>
index.html tartalma:
<html> <body> <h1>My HTTP server works</h1> <a href="/dead_link.html">Link not working</a> </body> </html>
JavaHTTPServer.java tartalma:
import java.io.BufferedOutputStream; import java.io.BufferedReader; import java.io.File; import java.io.FileInputStream; import java.io.FileNotFoundException; import java.io.IOException; import java.io.InputStreamReader; import java.io.OutputStream; import java.io.PrintWriter; import java.net.ServerSocket; import java.net.Socket; import java.util.Date; import java.util.StringTokenizer; public class JavaHTTPServer implements Runnable { static final File WEB_ROOT = new File("."); static final String DEFAULT_FILE = "index.html"; static final String FILE_NOT_FOUND = "404.html"; private Socket connect; public JavaHTTPServer(Socket c) { connect = c; } public static void main(String[] args) { try { ServerSocket serverConnect = new ServerSocket(8080); System.out.println("Server started.\nListening for connections on port : 8080 ...\n"); while (true) { JavaHTTPServer myServer = new JavaHTTPServer(serverConnect.accept()); Thread thread = new Thread(myServer); thread.start(); } } catch (IOException e) { System.err.println("Server Connection error : " + e.getMessage()); } } @Override public void run() { BufferedReader in = null; PrintWriter out = null; BufferedOutputStream dataOut = null; String fileRequested = null; try { in = new BufferedReader(new InputStreamReader(connect.getInputStream())); out = new PrintWriter(connect.getOutputStream()); dataOut = new BufferedOutputStream(connect.getOutputStream()); String input = in.readLine(); StringTokenizer parse = new StringTokenizer(input); String method = parse.nextToken().toUpperCase(); // we get the HTTP method of the client // we get file requested fileRequested = parse.nextToken().toLowerCase(); // we support only GET and HEAD methods, we check if (method.equals("GET") || method.equals("HEAD")) { // GET or HEAD method if (fileRequested.endsWith("/")) { fileRequested += DEFAULT_FILE; } File file = new File(WEB_ROOT, fileRequested); int fileLength = (int) file.length(); String content = getContentType(fileRequested); if (method.equals("GET")) { // GET method so we return content byte[] fileData = readFileData(file, fileLength); // send HTTP Headers out.println("HTTP/1.1 200 OK"); out.println("Server: Java HTTP Server v1.0"); out.println("Date: " + new Date()); out.println("Content-type: " + content); out.println("Content-length: " + fileLength); out.println(); // blank line between headers and content, very important ! out.flush(); // flush character output stream buffer dataOut.write(fileData, 0, fileLength); dataOut.flush(); } } } catch (FileNotFoundException fnfe) { try { fileNotFound(out, dataOut, fileRequested); } catch (IOException ioe) { System.err.println("Error with file not found exception : " + ioe.getMessage()); } } catch (IOException ioe) { System.err.println("Server error : " + ioe); } finally { try { in.close(); out.close(); dataOut.close(); connect.close(); // we close socket connection } catch (Exception e) { System.err.println("Error closing stream : " + e.getMessage()); } } } private byte[] readFileData(File file, int fileLength) throws IOException { FileInputStream fileIn = null; byte[] fileData = new byte[fileLength]; try { fileIn = new FileInputStream(file); fileIn.read(fileData); } finally { if (fileIn != null) fileIn.close(); } return fileData; } // return supported MIME Types private String getContentType(String fileRequested) { if (fileRequested.endsWith(".htm") || fileRequested.endsWith(".html")) return "text/html"; else return "text/plain"; } private void fileNotFound(PrintWriter out, OutputStream dataOut, String fileRequested) throws IOException { File file = new File(WEB_ROOT, FILE_NOT_FOUND); int fileLength = (int) file.length(); String content = "text/html"; byte[] fileData = readFileData(file, fileLength); out.println("HTTP/1.1 404 File Not Found"); out.println("Server: Java HTTP Server v1.0"); out.println("Date: " + new Date()); out.println("Content-type: " + content); out.println("Content-length: " + fileLength); out.println(); // blank line between headers and content, very important ! out.flush(); // flush character output stream buffer dataOut.write(fileData, 0, fileLength); dataOut.flush(); } }
Feladat: refaktoráljuk a kódot és szüntessük meg a többszörözött részeket. Készítsünk egy külön függvényt a HTTP válasz általános visszadásához:
out.println("HTTP/1.1 200 OK"); out.println("Server: Java HTTP Server v1.0"); out.println("Date: " + new Date()); out.println("Content-type: " + content); out.println("Content-length: " + fileLength); out.println(); // blank line between headers and content, very important ! out.flush(); // flush character output stream buffer
Feladat: módosítsuk a forráskódot, hogy képeket is vissza tudjon adni. Ehhez először <img src=“…> kiegészítést adjunk hozzá a index.html-nek és másoljunk egy tetszőleges képet a html-ek mellé.