2012-08-05 63 views
0

我有以下问题....的BufferedWriter冲不

  try 
      { 
       clientInput = new BufferedReader(new InputStreamReader(clientSocket.getInputStream())); 
       clientOutput = new BufferedWriter(new PrintWriter(clientSocket.getOutputStream())); 

       while(true) 
       { 
        String clientRequest = ""; 
        String tempStr = clientInput.readLine(); 

        while(tempStr != null && !tempStr.equals("null")) 
        { 
         System.out.println(tempStr); 
         clientRequest += tempStr + " "; 
         tempStr = clientInput.readLine(); 
        } 

        //Parse Request 
        ArrayList<String> tokenArray = parseRequest(clientRequest); 

        Calendar c = Calendar.getInstance(); 

        switch(tokenArray.get(0)) 
        { 
         case "GET": 
         { 
          clientOutput.write("HTTP/1.1 200 OK\r\n"); 
          clientOutput.write("Date: " + c.getDisplayName(0, Calendar.LONG, Locale.UK).toString() + "\r\n"); 
          clientOutput.write("Server: Java HTTP Server v1.0\r\n"); 
          clientOutput.flush(); 
          break; 
          //Write File 
         } 
         default: 
         { 
          clientOutput.write("500\r\n"); 
          clientOutput.flush(); 
         } 
        } 
       } 
      } 

每一件事情完全工作精细向上和直到clientOutput.write("HTTP.......线, 客户端只是一直等待,等待......我” ve试图冲洗每一个sucsessive写后,但什么都没有.....但这是奇怪的部分 - 如果我写入和flush之前的代码进入while循环的写在case "GET":完美的作品..... 。即

代码确实一直执行到

      clientOutput.flush(); 
          break; 
          //Write File 

   try 
      { 
       clientInput = new BufferedReader(new InputStreamReader(clientSocket.getInputStream())); 
       clientOutput = new BufferedWriter(new PrintWriter(clientSocket.getOutputStream())); 

       clientOutput.write("HTTP/1.1 200 OK\r\n"); 
       clientOutput.flush(); 

       while(true) 
       { 
        String clientRequest = ""; 
        String tempStr = clientInput.readLine(); 

        while(tempStr != null && !tempStr.equals("null")) 
        { 
         System.out.println(tempStr); 
         clientRequest += tempStr + " "; 
         tempStr = clientInput.readLine(); 
        } 

        //Parse Request 
        ArrayList<String> tokenArray = parseRequest(clientRequest); 

        Calendar c = Calendar.getInstance(); 

        switch(tokenArray.get(0)) 
        { 
         case "GET": 
         { 
          clientOutput.write("HTTP/1.1 200 OK\r\n"); 
          clientOutput.write("Date: " + c.getDisplayName(0, Calendar.LONG, Locale.UK).toString() + "\r\n"); 
          clientOutput.write("Server: Java HTTP Server v1.0\r\n"); 
          clientOutput.flush(); 
          break; 
          //Write File 
         } 

这里是用于客户端的代码

 Socket s = new Socket("localhost", 1337); 

     BufferedReader fromServer = new BufferedReader(new InputStreamReader(s.getInputStream())); 
     BufferedWriter toServer = new BufferedWriter(new PrintWriter(s.getOutputStream())); 

     toServer.write("GET index.html HTTP/1.1\r\n"); 
     toServer.write("HOST: 127.0.0.1\r\n"); 
     toServer.write("Connection: close\r\n"); 
     toServer.write("\r\n"); 
     toServer.write("null\r\n"); 
     toServer.flush(); 

     while(true) 
     { 
      String ss = fromServer.readLine(); 
      if(ss != null && !ss.equals("null")) 
       System.out.println(ss); 
     } 

服务器类:Strydom_A_201103578_P03

public class Strydom_A_201103578_P03 
{ 
    Thread[] threadArray = new Thread[5]; 
    int ClientCount = 0; 

    public Strydom_A_201103578_P03() throws ClientSizeExceededException 
    { 
     ServerSocket httpServer = null; 
    try 
    { 
     httpServer = new ServerSocket(1337); 
    } 
    catch (IOException ex) 
    { 
     Logger.getLogger(Strydom_A_201103578_P03.class.getName()).log(Level.SEVERE, null, ex); 
    } 

    while(true) 
    { 
     try 
     { 
      //Wait for connection 

      Socket clientSocket = httpServer.accept(); 

      if(ClientCount < 5) 
      { 
       threadArray[ClientCount] = new Thread(new clientHandler(clientSocket)); 
       threadArray[ClientCount].start(); 
       ClientCount++; 
      } 
      else 
      { 
       throw new ClientSizeExceededException(); 
      } 

     } 
     catch(IOException ex) 
     { 

     } 
     finally 
     { 

     } 
    } 
} 

class clientHandler implements Runnable 
{ 
    Socket clientSocket; 
    public clientHandler(Socket clientSocket) 
    { 
     this.clientSocket = clientSocket; 
    } 

    @Override 
    public void run() 
    { 
     BufferedReader clientInput = null; 
     BufferedWriter clientOutput = null; 

      try 
      { 
       clientInput = new BufferedReader(new InputStreamReader(clientSocket.getInputStream())); 
       clientOutput = new BufferedWriter(new PrintWriter(clientSocket.getOutputStream())); 

       clientOutput.write(" "); 
       clientOutput.flush(); 

       while(true) 
       { 
        String clientRequest = ""; 
        String tempStr = clientInput.readLine(); 

        while(tempStr != null && !tempStr.equals("null")) 
        { 
         System.out.println(tempStr); 
         clientRequest += tempStr + " "; 
         tempStr = clientInput.readLine(); 
        } 

        //Parse Request 
        ArrayList<String> tokenArray = parseRequest(clientRequest); 

        Calendar c = Calendar.getInstance(); 

        switch(tokenArray.get(0)) 
        { 
         case "GET": 
         { 
          clientOutput.write("HTTP/1.1 200 OK\r\n"); 
          clientOutput.write("Date: " + c.getDisplayName(0, Calendar.LONG, Locale.UK).toString() + "\r\n"); 
          clientOutput.write("Server: Java HTTP Server v1.0\r\n"); 
          clientOutput.flush(); 
          break; 
          //Write File 
         } 
         default: 
         { 
          clientOutput.write("500\r\n"); 
          clientOutput.flush(); 
         } 
        } 
       } 
      } 
      catch (IOException ex) 
      { 
       Logger.getLogger(Strydom_A_201103578_P03.class.getName()).log(Level.SEVERE, null, ex); 
      } 
      finally 
      { 
       try 
       { 
        clientInput.close(); 
        clientOutput.close(); 
       } 
       catch (IOException ex) 
       { 
        Logger.getLogger(Strydom_A_201103578_P03.class.getName()).log(Level.SEVERE, null, ex); 
       } 
      } 
    } 

    private ArrayList<String> parseRequest(String tempStr) 
    { 
     StringTokenizer httpTokens = new StringTokenizer(tempStr, " "); 
     ArrayList<String> tokens = new ArrayList<>(); 

     while(httpTokens.hasMoreTokens()) 
      tokens.add(httpTokens.nextToken()); 

     return tokens; 
    } 
} 


public static void main(String[] args) throws ClientSizeExceededException 
{ 
    new Strydom_A_201103578_P03(); 
} 

}

public class TestClient 
{ 

public TestClient() 
{ 
    try 
    { 
     Socket s = new Socket("localhost", 1337); 

     BufferedReader fromServer = new BufferedReader(new InputStreamReader(s.getInputStream())); 
     BufferedWriter toServer = new BufferedWriter(new PrintWriter(s.getOutputStream())); 

     toServer.write("GET index.html HTTP/1.1\r\n"); 
     toServer.write("HOST: 127.0.0.1\r\n"); 
     toServer.write("Connection: close\r\n"); 
     toServer.write("\r\n"); 
     toServer.write("null\r\n"); 
     toServer.flush(); 

     while(true) 
     { 
      String ss = fromServer.readLine(); 
      if(ss != null && !ss.equals("null")) 
       System.out.println(ss); 
     } 

    } 
    catch (UnknownHostException ex) 
    { 
     Logger.getLogger(TestClient.class.getName()).log(Level.SEVERE, null, ex); 
    } 
    catch (IOException ex) 
    { 
     Logger.getLogger(TestClient.class.getName()).log(Level.SEVERE, null, ex); 
    } 

} 



public static void main(String[] args) 
{ 
    new TestClient(); 
} 

}

客户端类:TestClient的

创建一个项目(或2),并运行文件

+0

我怀疑你会得到那么多。你确定你打破了'while(tempStr!= null &&!tempStr.equals(“null”))''循环吗? – 2012-08-05 15:29:13

+0

...嗨大卫...如所述的一切工作,直到那里 - 我用调试器通过代码 - 服务器正在写complte标题...并确实冲洗..... – 2012-08-05 15:31:04

+1

啊,好吧。我敢打赌,客户端收到了服务器发送的所有数据,并再次调用readLine。 (你还没有发送完整的HTTP响应,你期待客户做什么,但是等待其余的呢?) – 2012-08-05 15:32:11

回答

1

这里的问题是PrintWriter。它吞噬异常。将其更改为OutputStreamWriter。然后你会看到任何被吞噬的异常。一般来说,您应该通过网络避免PrintWriters和PrintOutputStreams。

0

你需要改变你的内在while循环来寻找客户的请求结束:

while(tempStr != null && !tempStr.equals("null")) 

到:

while(tempStr != null && !tempStr.equals("null") && !tempStr.equals("")) 

在发送请求后,客户端不会断开连接(导致null)。它会给你一个空行来表明它的请求结束。

为什么立即返回响应头的原因正在工作?也许客户端只读取200和(最终)断开连接?所以当你阅读客户的请求时,它会结束,最终你会得到一个null。


编辑:

所以运行你的代码,它工作正常,我。客户端和服务器都在发送和接收请求和响应。但是,服务器永远不会断开连接(客户端包含一个Connection: close标头),并且客户端继续在readLine()上阻止。毫不奇怪,当我在服务器端建立连接之后立即包含write()flush(),除了在客户端看到HTTP/1.1 200 OK两次之外,没有任何变化。也许你所需要做的就是在try/catch{}的末尾finally{}块中关闭clientSocket

+0

这就是我想的,但他发誓他会离开'while'循环。 (另外,这对于请求结束来说并不是真正正确的测试,这是对请求头结尾的正确测试。) – 2012-08-05 15:35:19

+0

我现在添加了客户端代码,以便您可以看到 - 我正在发送一个自己的''“ null“'退出..... – 2012-08-05 15:36:51

+0

@AidenStrydom我追加了我的答案 – 2012-08-05 15:53:53

0

只要做到这一点,它会工作..........

PrintWriter

clientOutput = new BufferedWriter(new PrintWriter(clientSocket.getOutputStream(), true));

+0

自动冲洗是我第一次尝试〜 – 2012-08-05 15:58:20

+0

它没有奏效? ?? – 2012-08-05 16:02:12

+0

不 - 不,它没有 – 2012-08-05 17:04:31

0

添加true作为第二个参数所以我现在结束了痛苦的futhering - 这里是我终于做到了....

我改变从BufferedReader/WriterDataInputstream/OutputStream这两个服务器和客户端读取器....它现在完美 - - !感谢大家

艾登

0

对我来说,它的工作原理。

*** BREAK LINE:此断行对于浏览器解析标题结尾和内容开始非常重要。没有它,冲洗不工作,响应不发送。

out.write("GET HTTP/1.0\r\n") 
out.write("Accept: text/plain, text/html, text/*\r\n") 
out.write("\r\n") // THIS BREAK LINE *** 
out.write("It Works") 
out.flush() 
out.close()