/* ** This file is part of Filius, a network construction and simulation software. ** ** Originally created at the University of Siegen, Institute "Didactics of ** Informatics and E-Learning" by a students' project group: ** members (2006-2007): ** André Asschoff, Johannes Bade, Carsten Dittich, Thomas Gerding, ** Nadja Haßler, Ernst Johannes Klebert, Michell Weyer ** supervisors: ** Stefan Freischlad (maintainer until 2009), Peer Stechert ** Project is maintained since 2010 by Christian Eibl <filius@c.fameibl.de> ** and Stefan Freischlad ** Filius is free software: you can redistribute it and/or modify ** it under the terms of the GNU General Public License as published by ** the Free Software Foundation, either version 2 of the License, or ** (at your option) version 3. ** ** Filius is distributed in the hope that it will be useful, ** but WITHOUT ANY WARRANTY; without even the implied ** warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR ** PURPOSE. See the GNU General Public License for more details. ** ** You should have received a copy of the GNU General Public License ** along with Filius. If not, see <http://www.gnu.org/licenses/>. */ package filius.software.www; import java.io.BufferedReader; import java.io.FileReader; import java.util.HashMap; import java.util.StringTokenizer; import javax.swing.tree.DefaultMutableTreeNode; import filius.Main; import filius.rahmenprogramm.Base64; import filius.rahmenprogramm.Information; import filius.software.clientserver.TCPServerAnwendung; import filius.software.system.Datei; import filius.software.system.Dateisystem; import filius.software.system.InternetKnotenBetriebssystem; import filius.software.transportschicht.Socket; import filius.software.transportschicht.TCPSocket; /** * Anwendungklasse des Webservers * */ public class WebServer extends TCPServerAnwendung { private DefaultMutableTreeNode verzeichnis; private HashMap<String, WebServerPlugIn> plugins = new HashMap<String, WebServerPlugIn>(); private String[][] vHostArray = new String[5][2]; // default size of 5x2 public WebServer() { super(); port = 80; this.resetVHosts(); } public void resetVHosts() { for(int i=0; i<vHostArray.length; i++) { vHostArray[i][0]=""; vHostArray[i][1]=""; } this.benachrichtigeBeobachter(); } /** * nachdem ein WebServer erzeugt wurde, muss ueber die Vaterklasse Anwendung * ein Betriebssystem zugewiesen werden */ public void setSystemSoftware(InternetKnotenBetriebssystem betriebssystem) { Main.debug.println("INVOKED ("+this.hashCode()+", T"+this.getId()+") "+getClass()+" (WebServer), setSystemSoftware("+betriebssystem+")"); super.setSystemSoftware(betriebssystem); erzeugeStandardVerzeichnis(); } public void setzePlugIn(WebServerPlugIn pi) { plugins.put(pi.getPfad(), pi); } public void erzeugeIndexDatei(String dateipfad) { Main.debug.println("INVOKED ("+this.hashCode()+", T"+this.getId()+") "+getClass()+" (WebServer), erzeugeIndexDatei("+dateipfad+")"); BufferedReader dateiPuffer; StringBuffer fullFile; String input; try { dateiPuffer = new BufferedReader(new FileReader(dateipfad)); fullFile = new StringBuffer(); while ((input = dateiPuffer.readLine()) != null) { fullFile.append(input + "\n"); } erzeugeDatei("index", "html", fullFile.toString()); } catch (Exception e) { e.printStackTrace(Main.debug); } } public byte[] inputStreamToBytes(java.io.InputStream in) { java.io.ByteArrayOutputStream out = new java.io.ByteArrayOutputStream(1024); byte[] buffer = new byte[1024]; int len; try{ while((len = in.read(buffer)) >= 0) out.write(buffer, 0, len); in.close(); out.close(); } catch ( java.io.IOException e ) { Main.debug.println("EXCEPTION ("+this.hashCode()+", T"+this.getId()+") "+getClass()+" (WebServer): IOException in conversion of InputStream to Byte[]"); e.printStackTrace(Main.debug); } return out.toByteArray(); } /** * erzeugt alle Dateien, fuer Fehlermeldungen etc. Die Dateien liegen als * Textdateien im realen Ordner /konfig */ private void erzeugeStandardVerzeichnis() { Main.debug.println("INVOKED ("+this.hashCode()+", T"+this.getId()+") "+getClass()+" (WebServer), erzeugeStandardVerzeichnis()"); Dateisystem dateisystem; dateisystem = getSystemSoftware().getDateisystem(); dateisystem.erstelleVerzeichnis(dateisystem.getRoot(), "webserver"); verzeichnis = dateisystem.verzeichnisKnoten(dateisystem.holeRootPfad() + Dateisystem.FILE_SEPARATOR + "webserver"); try { if (!dateisystem.dateiVorhanden(verzeichnis, "index.html")) { erzeugeIndexDatei(Information.getInformation().getProgrammPfad() + "config/webserver_index.txt"); // this was used for externally stored file... no longer working // erzeugeDatei("splashscreen-mini", "png", Base64 // .encodeFromFile(Information.getInformation().getProgrammPfad() // + "gfx/allgemein/splashscreen-mini.png")); erzeugeDatei("splashscreen-mini", "png", Base64.encodeBytes(inputStreamToBytes(getClass().getResourceAsStream("/gfx/allgemein/splashscreen-mini.png")))); } } catch (Exception e) { e.printStackTrace(Main.debug); } } /** * erzeugt eine Datei fuer das Dateisystem von Filius. Dieses arbeitet mit * TreeNodes */ private void erzeugeDatei(String dateiname, String endung, String quellcode) { Main.debug.println("INVOKED ("+this.hashCode()+", T"+this.getId()+") "+getClass()+" (WebServer), erzeugeDatei("+dateiname+","+endung+","+quellcode+")"); String kompletteDateiName = dateiname + "." + endung; Datei datei = new Datei(kompletteDateiName, endung, quellcode); getSystemSoftware().getDateisystem().speicherDatei(verzeichnis, datei); } /** * holt eine Datei aus dem Verzeichnisbaum des WebServers. Dieser benutzt * TreeNodes */ protected Datei dateiLiefern(String relativerPfad) { Main.debug.println("INVOKED ("+this.hashCode()+", T"+this.getId()+") "+getClass()+" (WebServer), dateiLiefern("+relativerPfad+")"); Datei tmpDatei; tmpDatei = getSystemSoftware().getDateisystem().holeDatei(verzeichnis, relativerPfad); return tmpDatei; } /** * sucht nach einem bestimmten PlugIn. Zum Beispiel fuer eine Firewall * Bisher installierte PlugIns: /konfig.html & /log.html * */ public WebServerPlugIn holePlugin(String key) { Main.debug.println("INVOKED ("+this.hashCode()+", T"+this.getId()+") "+getClass()+" (WebServer), holePlugin("+key+")"); WebServerPlugIn plugIn = null; if (plugins.containsKey(key)) { plugIn = (WebServerPlugIn) plugins.get(key); } return plugIn; } public HashMap<String, WebServerPlugIn> getPlugins() { return plugins; } public void setPlugins(HashMap<String, WebServerPlugIn> plugins) { this.plugins = plugins; } public String printVHostTable() { String result = ""; for(int i=0; i<vHostArray.length; i++) { result+=i+":\t"; if(vHostArray[i][0]==null) result+="<null>\t"; else result+=vHostArray[i][0]+"\t"; if(vHostArray[i][1]==null) result+="<null>\n"; else result+=vHostArray[i][1]+"\n"; } return result; } public void changeVHostTable(int row, int col, String val) { Main.debug.println("INVOKED ("+this.hashCode()+", T"+this.getId()+") "+getClass()+" (WebServer), changeVHostTable("+row+","+col+","+val+")"); if(val!=null) vHostArray[row][col] = val; else vHostArray[row][col] = ""; // Main.debug.println("DEBUG WebServer: vHostArray (danach):\n"+printVHostTable()); this.saveVHosts(); } public String vhostPrefix(String vhost) { Main.debug.println("INVOKED ("+this.hashCode()+", T"+this.getId()+") "+getClass()+" (WebServer), vhostPrefix("+vhost+")"); for(int i=0; i<vHostArray.length; i++) { if(vHostArray[i][0]!=null && vHostArray[i][0].equalsIgnoreCase(vhost)) { if(vHostArray[i][1] != null) return vHostArray[i][1]; } } return ""; } public String[][] getVHostArray() { return vHostArray; } protected void neuerMitarbeiter(Socket socket) { Main.debug.println("INVOKED ("+this.hashCode()+", T"+this.getId()+") "+getClass()+" (WebServer), neuerMitarbeiter("+socket+")"); WebServerMitarbeiter wsMitarbeiter; if (socket instanceof TCPSocket) { wsMitarbeiter = new WebServerMitarbeiter(this, (TCPSocket)socket); wsMitarbeiter.starten(); mitarbeiter.add(wsMitarbeiter); } } public void starten() { Main.debug.println("INVOKED ("+this.hashCode()+", T"+this.getId()+") "+getClass()+" (WebServer), starten()"); super.starten(); if (!getSystemSoftware().getDateisystem().dateiVorhanden("www.conf", "vhosts")) { getSystemSoftware().getDateisystem().erstelleVerzeichnis("root", "www.conf"); } initialisiereVHosts(); } public void beenden() { Main.debug.println("INVOKED ("+this.hashCode()+", T"+this.getId()+") "+getClass()+" (WebServer), beenden()"); super.beenden(); } private void saveVHosts() { Main.debug.println("INVOKED ("+this.hashCode()+", T"+this.getId()+") "+getClass()+" (DNSServer), schreibeRecordListe()"); Datei vhosts; StringBuffer text; Dateisystem dateisystem; String host, directory; dateisystem = getSystemSoftware().getDateisystem(); text = new StringBuffer(); for(int i=0; i<vHostArray.length; i++) { host = vHostArray[i][0]; directory = vHostArray[i][1]; text.append((host != null ? host : "") + "\n" + (directory != null ? directory : "") + "\n"); } vhosts = new Datei(); vhosts.setDateiInhalt(text.toString()); vhosts.setName("vhosts"); dateisystem.speicherDatei(dateisystem.holeRootPfad()+Dateisystem.FILE_SEPARATOR+"www.conf", vhosts); } private void initialisiereVHosts() { Main.debug.println("INVOKED ("+this.hashCode()+", T"+this.getId()+") "+getClass()+", initialisiereVHosts()"); Datei vhosts; StringTokenizer tokenizer; String line; Dateisystem dateisystem; vHostArray = new String[5][2]; int row=0; int col=0; dateisystem = getSystemSoftware().getDateisystem(); vhosts = dateisystem.holeDatei(dateisystem.holeRootPfad()+Dateisystem.FILE_SEPARATOR+"www.conf"+Dateisystem.FILE_SEPARATOR+"vhosts"); if (vhosts != null) { tokenizer = new StringTokenizer(vhosts.getDateiInhalt(), "\n"); while (tokenizer.hasMoreTokens()) { line = tokenizer.nextToken().trim(); vHostArray[row][col] = line; if(col==0) { col++; } else { col=0; row++; } } } for (; row < 5; row++) { vHostArray[row][0] = ""; vHostArray[row][1] = ""; } } }