【问题标题】:Java, sockets, BufferedReader, and readline hang ... :(Java、套接字、BufferedReader 和 readline 挂起 ... :(
【发布时间】:2009-10-16 12:16:53
【问题描述】:

我根本不是 Java 程序员。实际上,我试图不惜一切代价避免它,但我必须在课堂上使用它(在学校意义上)。老师要求我们使用Socket()、BufferedReader()、PrintWriter()等各种东西,包括BufferedReader()的readLine()方法。

基本上,这就是我遇到的问题。文档明确指出 readLine 应该在输入流的末尾返回 null,但这不是正在发生的事情。

Socket link       = new Socket(this.address, 80);
BufferedReader in = new BufferedReader( new InputStreamReader( link.getInputStream() ));
PrintWriter   out = new PrintWriter(    new PrintWriter(       link.getOutputStream(), true ));

out.print("GET blah blah blah"); // http request by hand
out.flush(); // send the get please

while( (s=in.readLine()) != null ) {

    // prints the html correctly, hooray!!
    System.out.println(s);
}

我没有在 HTML 末尾完成,而是得到一个空行、一个 0 和 另一个空行,然后下一个 in.readLine() 永远挂起。为什么? 我的 null 呢?

我尝试了 out.close() 看看是否可能是 Yahoo!正在做一个持久的http 会话或其他东西(我认为没有标题就不会 我们愿意这样做)。

我在网上找到的所有 Java 套接字示例似乎都表明 while 循环是正确的形式。我只是不知道足够的 Java 来调试 这个。

【问题讨论】:

    标签: java sockets


    【解决方案1】:

    您的问题是内容编码“分块”。当响应开始时从 Web 服务器请求的内容的长度未知时使用此选项。它基本上由正在发送的字节数组成,然后是CRLF,然后是字节。响应的结束由您看到的确切顺序表示。 Web 服务器现在正在等待您的下一个请求(这也称为“请求管道”)。

    你有几种可能:

    • 使用 HTTP 1.0 版。这将导致网络服务器在完全发送响应后自动关闭连接。
    • 在发送请求时指定“Connection: close”标头。这也会关闭连接。
    • 正确解析“分块”的内容编码,并简单地将其视为响应现已完成——它就是这样。

    【讨论】:

    • 这是有道理的。我需要检查标题。我只是打算使用http1.0。
    • 是的,学校锻炼是最明智的做法。
    【解决方案2】:

    所以你正在从一个套接字读取(你没有在你的代码中显示,但这就是我从文本中收集到的)?

    只要对方没有关闭连接,Java就不知道在输入的末尾,所以readLine()在等待对方发送更多数据,不返回@987654322 @。

    【讨论】:

    • ... 从套接字读取,是的。我将其添加到问题中,谢谢。
    【解决方案3】:

    如果没有 2 个回车 + 换行对,您的 HTTP 请求是不完整的。您可能还应该在请求发送后调用 close:

    out.print("GET /index.html HTTP/1.0\r\n");
    // maybe print optional headers here
    // empty line
    out.print("\r\n");
    out.flush();
    out.close();
    

    【讨论】:

      猜你喜欢
      • 2011-08-24
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-06-06
      • 2011-12-12
      • 2015-06-07
      • 1970-01-01
      • 2015-05-26
      相关资源
      最近更新 更多