2012-05-28 20 views
22

Ich bin derzeit einen kleinen HTTP-Server erstellen, die eine statische Seite zurück <p>Hello!</p> ... Ich habe versucht, mit Steckdosen mit Java:Ein einfacher HTTP-Server mit Java/Socket?

public static void main(String[] args) throws Exception { 

     // création de la socket 
     int port = 1989; 
     ServerSocket serverSocket = new ServerSocket(port); 
     System.err.println("Serveur lancé sur le port : " + port); 

     // repeatedly wait for connections, and process 
     while (true) { 

      // on reste bloqué sur l'attente d'une demande client 
      Socket clientSocket = serverSocket.accept(); 
      System.err.println("Nouveau client connecté"); 

      // on ouvre un flux de converation 

      BufferedReader in = new BufferedReader(
          new InputStreamReader(clientSocket.getInputStream()) 
         ); 
      PrintWriter out = new PrintWriter(
         new BufferedWriter(
          new OutputStreamWriter(clientSocket.getOutputStream())), 
         true); 

      // chaque fois qu'une donnée est lue sur le réseau on la renvoi sur le flux d'écriture. 
      // la donnée lue est donc retournée exactement au même client. 
      String s; 
      while ((s = in.readLine()) != null) { 
       System.out.println(s); 


     out.write("HTTP/1.0 200 OK\r\n"); 
     out.write("Date: Fri, 31 Dec 1999 23:59:59 GMT\r\n"); 
     out.write("Server: Apache/0.8.4\r\n"); 
     out.write("Content-Type: text/html\r\n"); 
     out.write("Content-Length: 59\r\n"); 
     out.write("Expires: Sat, 01 Jan 2000 00:59:59 GMT\r\n"); 
     out.write("Last-modified: Fri, 09 Aug 1996 14:21:40 GMT\r\n"); 
     out.write("\r\n"); 
     out.write("<TITLE>Exemple</TITLE>"); 
     out.write("<P>Ceci est une page d'exemple.</P>"); 
    } 

      // on ferme les flux. 
      System.err.println("Connexion avec le client terminée"); 
      out.close(); 
      in.close(); 
      clientSocket.close(); 
     } 
    } 

dieser Code keine Fehler enthält, und ich bekam eine Antwort von dem Browser wie this:

GET/HTTP/1.1 
Host: localhost:1989 
Connection: keep-alive 
User-Agent: Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/536.5 (KHTML, like Gecko) Chrome/19.0.1084.46 Safari/536.5 Comodo_Dragon/19.0.3.0 
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8 
Accept-Encoding: gzip,deflate,sdch 
Accept-Language: fr-FR,fr;q=0.8,en-US;q=0.6,en;q=0.4 
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.3 

Aber mein Problem ist, dass ich keine Seite im Browser bekomme? Irgendwelche Hilfe bitte?

PS: ich diesen Artikel bereits gelesen: http://en.wikipedia.org/wiki/Hypertext_Transfer_Protocol, (im sorry für die Sprache Französisch ...)

Antwort

29

Zusätzlich zu den \ r \ n nach jeder Anfrage Kopfzeile, müssen Sie eine leere Zeile nach der Kopfzeile senden. Beispiel:

out.write("HTTP/1.0 200 OK\r\n"); 
// Header... 
out.write("Last-modified: Fri, 09 Aug 1996 14:21:40 GMT\r\n"); 
out.write("\r\n"); // The content starts afters this empty line 
out.write("<TITLE>Hello!</TITLE>"); 
// Content... 

korrigierte ich Ihren Code, so dass es funktioniert (aber es ist noch nicht perfekt, Sie jede Anfrage in einem separaten Thread behandeln sollen, zB mit java.util.concurrent.ThreadPoolExecutor):

public static void main(String[] args) throws Exception { 
    // création de la socket 
    int port = 1989; 
    ServerSocket serverSocket = new ServerSocket(port); 
    System.err.println("Serveur lancé sur le port : " + port); 

    // repeatedly wait for connections, and process 
    while (true) { 
     // on reste bloqué sur l'attente d'une demande client 
     Socket clientSocket = serverSocket.accept(); 
     System.err.println("Nouveau client connecté"); 

     // on ouvre un flux de converation 

     BufferedReader in = new BufferedReader(new InputStreamReader(clientSocket.getInputStream())); 
     BufferedWriter out = new BufferedWriter(new OutputStreamWriter(clientSocket.getOutputStream())); 

     // chaque fois qu'une donnée est lue sur le réseau on la renvoi sur 
     // le flux d'écriture. 
     // la donnée lue est donc retournée exactement au même client. 
     String s; 
     while ((s = in.readLine()) != null) { 
      System.out.println(s); 
      if (s.isEmpty()) { 
       break; 
      } 
     } 

     out.write("HTTP/1.0 200 OK\r\n"); 
     out.write("Date: Fri, 31 Dec 1999 23:59:59 GMT\r\n"); 
     out.write("Server: Apache/0.8.4\r\n"); 
     out.write("Content-Type: text/html\r\n"); 
     out.write("Content-Length: 59\r\n"); 
     out.write("Expires: Sat, 01 Jan 2000 00:59:59 GMT\r\n"); 
     out.write("Last-modified: Fri, 09 Aug 1996 14:21:40 GMT\r\n"); 
     out.write("\r\n"); 
     out.write("<TITLE>Exemple</TITLE>"); 
     out.write("<P>Ceci est une page d'exemple.</P>"); 

     // on ferme les flux. 
     System.err.println("Connexion avec le client terminée"); 
     out.close(); 
     in.close(); 
     clientSocket.close(); 
    } 
} 
+1

Ich habe das versucht, aber es funktioniert immer noch nicht ... (siehe mein Update). –

+0

Ihre Anfrage Header lesen While-Schleife ist falsch. Ich werde meiner Antwort ein funktionierendes Beispiel hinzufügen. –

+0

Joel, du hast vergessen den Ausgangsstrom in deinem Beispiel zu löschen. Wenn Sie dieses Stück Code mit viel HTML versuchen, funktioniert es nicht richtig. –

1

Welche Maschine sind Sie mit? Welches OS? Wenn Sie einen UNIX-Computer ausführen, funktioniert println nicht, da nur ein LF-Zeichen gesendet wird. HTTP benötigt CR und LF für seine Header. Versuchen Sie, \ r am Ende Ihrer Strings hinzuzufügen und sehen Sie, ob das funktioniert.

Oh, auch IhrFormal:

out.println("HTTP/1.0 200 OK"+ 
"Date: Fri, 31 Dec 1999 23:59:59 GMT"+ 
"Server: Apache/0.8.4"+ 
"Content-Type: text/html"+ 
"Content-Length: 59"+ 
"Expires: Sat, 01 Jan 2000 00:59:59 GMT"+ 
"Last-modified: Fri, 09 Aug 1996 14:21:40 GMT"+ 

Es ist das Drucken einen einzigen langen String.

Ändern Sie diese in eine println für jede Zeichenfolge oder fügen Sie \ r \ n in die Zeichenfolge hinzu.

+0

Danke!, Ich habe Windows7, ich habe es versucht, aber immer noch nicht funktioniert .... –

+0

=> out.flush(); –

1

Sie benötigen die richtigen Zeilenseparatoren (\r\n) zwischen jedem Zeilenausgang. Es ist nicht genug, sie einfach zu verketten - was Sie sehen können, wenn Sie die Antwort ausdrucken.

+0

Er braucht \ r \ n. Das ist HTTP. – EJP

4

Dies ist eine Antwort nur auf Ihre letzte Frage und der Grund, dass nichts im Browser sichtbar ist, ist, weil Sie die Anzahl der Zeichen falsch berechnet haben.

Es sollte 57 sein Besser statt 59.

noch ist die Anzahl der Zeichen automatisch berechnet zu haben, aber ich glaube, dass Ihre Probe nur ein Beispiel ist.

+1

Oh, das hat für mich funktioniert. Es sollte auf der Oberseite sein :) –

Verwandte Themen