Длительный опрос с NSURLConnection
Я работаю над приложением iPhone, которое будет использовать длинный опрос для отправки уведомлений о событиях с сервера клиенту через HTTP. После открытия соединения на сервере я отправляю небольшие биты JSON, которые представляют события, по мере их возникновения. Я обнаружил, что -[NSURLConnectionDelegate connection:didReceiveData]
не вызывается до тех пор, пока я не закрою соединение, независимо от настроек кеша, которые я использую при создании NSURLRequest
. Я проверял, что конец сервера работает как ожидалось - первое событие JSON будет отправлено немедленно, и последующие события будут отправляться по проводу по мере их возникновения. Есть ли способ использовать NSURLConnection
для получения этих событий по мере их возникновения, или мне нужно будет вместо этого перейти к API CFSocket?
Я начинаю работать над интеграцией CocoaAsyncSocket, но предпочитаю продолжать использовать NSURLConnection
, если это возможно, так как он намного лучше подходит для остальной части структуры веб-сервиса, основанной на REST/JSON.
Ответы
Ответ 1
NSURLConnection
будет буферизовать данные во время их загрузки и вернуть все это вам в один кусок с помощью метода didReceiveData
. Класс NSURLConnection
не может определить разницу между задержкой сети и преднамеренным разделением данных.
Вам следует либо использовать сетевой API нижнего уровня, как CFSocket, как вы упомянули (у вас будет доступ к каждому байту, как он поступает из сетевого интерфейса, и может различать две части вашей полезной нагрузки), или вы можно посмотреть в библиотеке, например CURL, и посмотреть, какие типы буферизации/небуферизации вывода там есть.
Ответ 2
Я столкнулся с этим сегодня. Я написал свой собственный класс для обработки этого, который имитирует основные функции NSURLConnection.
http://github.com/nall/SZUtilities/blob/master/SZURLConnection.h
Ответ 3
Звучит так, как будто вам нужно сбросить сокет на стороне сервера, хотя это действительно сложно сказать наверняка. Если вы не можете легко изменить сервер, чтобы сделать это, то это может помочь обнюхать сетевое подключение, чтобы увидеть, когда материал действительно отправляется с сервера.
Вы можете использовать такой инструмент, как Wireshark, чтобы обнюхать вашу сеть.
Еще одна опция для просмотра того, что отправляется/принимается на/с телефона, описано в следующей статье:
http://blog.jerodsanto.net/2009/06/sniff-your-iphones-network-traffic/
Удачи!
Ответ 4
В настоящее время мы делаем R & D для переноса наших библиотек комет StreamLink на iPhone.
Я обнаружил, что в эмуляторе вы начнете получать обратные вызовы didReceiveData после получения 1KB данных. Таким образом, вы можете отправить нежелательный блок 1 КБ, чтобы начать получать обратные вызовы. Кажется, что на устройстве, однако, этого не происходит. В сафари (на устройстве) вам нужно отправить 2 КБ, но с использованием NSURLConnection я тоже не получаю обратных вызовов. Похоже, мне, возможно, придется придерживаться того же подхода.
Я также могу играть с multipart-replace и некоторыми другими более новыми заголовками и типами mime, чтобы увидеть, помогает ли это стимулировать NSURLConnection.
Ответ 5
Существует еще одна реализация API HTTP с именем ASIHttpRequest. Он не имеет проблемы, указанной выше, и предоставляет полный набор инструментов практически для каждой функции HTTP, включая загрузку файлов, файлы cookie, аутентификацию,...
http://allseeing-i.com/ASIHTTPRequest/