2013-04-17 3 views
2

У меня действительно странная проблема при работе с сокетами Java. Эта проблема происходит только для ОЧЕНЬ малого подмножества URL-адресов, которые я обрабатываю. Назовем пример url abc.com.Ядро сокета чтения блокируется бесконечно

Редактировать: url is lists.wikimedia.org/robots.txt, что дает мне проблемы.

Я могу завивать/netcat/telnet lists.wikimedia.org с путём /robots.txt отлично отлично. Telnet даже сообщает мне IP-адрес для lists.wikimedia.org (см. Ниже). Однако, когда я пытаюсь не делать то же самое с помощью Java-сокет, как следующие:

Socket s = new Socket("208.80.154.4", 80); // IP is same as the IP printed by telnet 
BufferedWriter writer = new BufferedWriter(s.getOutputStream()); 
writer.println("HEAD /robots.txt HTTP/1.1"); 
writer.println("Host: lists.wikimedia.org"); 
writer.println("Connection: Keep-Alive"); 
writer.flush(); 

InputStreamReader r = new InputStreamReader(s.getInputStream()); 
BufferedReader reader = new BufferedReader(r); 

String line; 
while ((line = reader.readLine()) != null) { 
    ... 
} 

The Readline блоки бесконечно до времен гнездовых выходят ...

Кто-нибудь есть какие-либо идеи, почему это может случаться? Тот же код отлично работает с большинством других URL-адресов, и достаточно интересно, что эта ошибка возникает только для некоторых запросов ROBOTS.TXT ... Я так смущен, почему это может произойти.

Edit:

Интересно, что с помощью Apache HttpClient библиотека дает мне правильный результат для lists.wikimedia.org/robots.txt. Есть ли что-то еще, что мне нужно сделать, если я хочу вручную сделать это через Socket?

+2

'Socket' не имеет метода readLine(). –

+4

Вы не можете просто открыть сокет и ожидать, что он вам что-то даст. Вам нужно будет показать еще какой-нибудь код, если вы хотите лучше помочь раньше. – ddmps

+0

Как и в случае, отправьте правильно отформатированный HTTP-запрос. –

ответ

5

Возможно, вам не хватает дополнительного CRLF для завершения заголовка HTTP-запроса. Я также хотел бы написать их в явном виде, чтобы избежать платформ замешательства, как так (непроверенные):

writer.print("HEAD /robots.txt HTTP/1.1\r\n"); 
writer.print("Host: lists.wikimedia.org\r\n"); 
writer.print("Connection: Keep-Alive\r\n"); 
writer.print("\r\n"); 
writer.flush(); 

также рассмотреть возможность использования HttpURLConnection вместо простых розеток, забирает весь этот burdons:

HttpURLConnection connection = (HttpURLConnection) new URL(url).openConnection(); 
connection.setRequestMethod("HEAD"); 
... 
+0

СПАСИБО, \ r \ n работал, НИКОГДА НЕ ИСПОЛЬЗУЯ PRINTLN СНОВА – Jin

+0

Мне нужно использовать Socket, потому что это назначение haha ​​ – Jin

+0

Одна из типичных ошибок «write once, run everwhere» Java. (Ловушки, используемые здесь, чтобы избежать слова «ложь»). С другой стороны, было бы полезно иметь правильное поведение новой строки на каждой платформе, не заботясь о ней. –

Смежные вопросы