Работа с инкрементным ответом сервера в AJAX (в JavaScript)

У меня есть приложение AJAX, которое обновляет страницу в зависимости от ответа сервера. Команда, на которой основан ответ сервера AJAX, требует много времени для генерации полного ответа, но она отправляет частичную информацию, как только она рассчитывается. Этот частичный ответ / частичная информация отправляется «пакетом», и время и размер каждого пакета непредсказуемы. В сценарии CGI (на Perl), передающем вывод команды в веб-браузер (в запрос AJAX), включена автозапуск.

Ответ сервера основан на выводе внешней команды. В то время как 'time cmd> / dev / null' дает в среднем около 10,0 секунд, 'time cmd | head> / dev / null' дает меньше 0,1 секунды (например, данные). Все данные являются результатом одного вызова этой внешней команды .

Ситуация выглядит следующим образом (следует диаграмма ASCII-art):

 client |     | server
---------     ---------

request -\
          \
           \
            \
             \->

             /- response
            /      .
           /       .
          /  /-    .
       <-/  /      . 
           /       .
          /  /-  [end]
       <-/  /
           /
          /
       <-/

У меня есть несколько вопросов по этой проблеме.

Примечание. серверная часть выполняется как сценарий CGI в Perl, и я бы предпочел (также) увидеть решение без использования библиотеки / фреймворка JavaScript, например jQuery.

  • Вывод команды, используемой серверной частью приложения AJAX, основан на строчности. Каждая группа строк, начиная с одного определенного типа строки и заканчивая другим типом строки, состоит из независимых и неизменяемых данных. Должен ли я просто передавать ответ от команды как «текст / простой» и выполнять обработку в JavaScript на стороне клиента, или я должен предварительно обрабатывать данные на сервере и отправлять целые фрагменты данных в виде JSON с использованием типа mimetype «application / json»?

  • Может случиться так, что за большим фрагментом данных, отправленным сервером сразу, вскоре последует еще один фрагмент данных. Как быть в ситуации, когда обработчик onreadystatechange вызывается, когда предыдущий вызов не завершился? Должен ли я использовать глобальную переменную в качестве семафора или передать переменную состояния в качестве параметра обработчика (ну, использовать xhr.onreadystatechange = function() { handleRequest(xhr, state) })?

  • Должен ли я использовать для этого «text / plain» или «application / json» или, возможно, «multipart / x0mixed-replace»? Примечание: это приложение должно работать (почти) в любом браузере.

  • Как работать с веб-браузером (движками JavaScript), который вызывает onReadyStateChange только после получения полного ответа (поэтому я не вижу xhr.readyState == 3, т.е. частичный ответ более одного раза)? Ну, помимо использования какой-то инфраструктуры JavaScript.

  • Как поступать с неполными ответами (которые в данной ситуации означают неполные строки).

  • Должен ли я отправить маркер конца ответа, или полагаться на счетчик, чтобы проверить, получили ли мы все данные, или я могу просто полагаться на обнаружение xhr.readyState == 4?

Даже частичный ответ был бы полезен.


person Jakub Narębski    schedule 20.07.2009    source источник


Ответы (2)


Я думаю, что Comet - это часть того, что вам нужно для вашего решения. Вы можете дополнительно (если я правильно понял) ознакомиться с протоколом Байё, который был реализовано Фондом Додзё. Все это все еще очень новое (хотя некоторые из них могут быть возможны с первыми реализациями HTML5).

Кроме того, вам, вероятно, придется реализовать метод опроса. Другой вопрос: сколько данных может обработать клиентский интерпретатор JavaScript. Есть ли у вас какая-то возможность каким-то образом "публиковать" свои данные, чтобы у вас не было проблемы с обработкой запроса, который все еще обрабатывается, пока уже поступает другой ответ?

person Daff    schedule 20.07.2009

Я думаю, что клиентская сторона может быть спроектирована так, чтобы обрабатывать данные по частям, отправляя повторяющиеся запросы AJAX, пока все данные не будут предоставлены. Это предполагает, что каждый фрагмент может быть отправлен своевременно (без проблем с тайм-аутом на стороне клиента), даже если весь ответ был большим; и этот дизайн, вероятно, проще, чем разработка проверок конкретных статусов частичного ответа, которые могут отличаться от браузера к браузеру.

Что касается того, выполняете ли вы обработку на стороне сервера или на стороне клиента, это будет зависеть, например, от сколько одновременных клиентов вам нужно будет обслуживать и можно ли использовать кеширование для каких-либо ответов; в некоторых сценариях, где много клиентов, лучше переложить часть вычислительной нагрузки на них (если, конечно, они могут с ней справиться).

person Vinay Sajip    schedule 20.07.2009
comment
Проблема с повторяющимися запросами AJAX (стратегия длительного опроса) заключается в том, что данные генерируются с помощью single команды, поэтому серверная часть AJAX должна сохранять состояние / запоминать состояние клиента / передавать для отправки дальнейших запросов. . - person Jakub Narębski; 21.07.2009