我想实现POP3客户端。我知道在POP3协议中,每条消息都以\r\n
结尾。我想在Java中编写一个recvuntil
方法,它将能够立即接收整个消息。
Python非常简单:
def recv_all_until_ver3(s, crlf):
data = ""
while data[-len(crlf):] != crlf:
data += s.recv(1)
return data
然而,当我尝试在Java中做同样的事情时:
class JavaApplication1 {
/**
* @param args the command line arguments
*/
public static void main(String[] args) throws IOException {
// TODO code application logic here
String serverAddress = "interia.pl";
int port = 110;
Socket s = new Socket(serverAddress, port);
BufferedReader input = new BufferedReader(new InputStreamReader(s.getInputStream()));
String answer = "";
while (!answer.contains("\r\n")) {
answer = input.readLine();
System.out.println(answer);
}
}
}
它收到一条消息和手而不是结束本身。有没有办法在Java中实现这个方法?我可以一个一个地读取字符,而不是整行,直到我在消息中找到\r\n
为止?谢谢。
答案 0 :(得分:1)
Python代码一次读取一个八位字节,立即将其附加到answer
,如果当前迭代answer
以CRLF
结尾,则表示已完成。
Java代码挂起,因为BufferedReader.readLine()
在删除行终止后返回行内容。此时answer
不包含CRLF
,因此再次调用readLine()
,因为流未从另一端关闭(您的程序将抛出NullPointerException
并且你有一个无限的读取超时(你会看到一个SocketTimeoutException
),它会挂起,永远等待下一行。
正确的版本是
Socket socket = connect(); // Implement this
Scanner scanner = new Scanner(new InputStreamReader(socket.getInputStream(), "ASCII"));
scanner.useDelimiter("\r\n");
String response = scanner.nextLine();
socket.close();
注意:
答案 1 :(得分:0)
您可以使用Scanner类(它接受InputStream
作为构造函数参数)并使用useDelimiter
方法设置分隔符。阅读以\r\n