Веб-чат XMPP: как разрешить несколько вкладок/окон?

У нас есть сайт, и мы разработали систему чата для него, используя библиотеку strophe.js и ejabberd XMPP-сервер. Мы используем привязку сеанса, которая была инициирована с помощью PHP (с использованием внутренней библиотеки). Мы делаем RID и SID из PHP script, а затем используем привязку сеанса в стиле. Указанные RID и SID хранятся в файле cookie, а значение RID в файле cookie обновляется при каждом обновлении RID на strophe.js. (Это значит, что мы можем повторно использовать идентификатор сеанса на странице обновления/навигации в других местах на сайте)

Теперь мы планируем работать с несколькими вкладками/окнами. Я наблюдал реализацию Facebook, и для каждой вкладки есть длинный запрос опроса в определенном домене. Этот домен отличается для каждой вкладки. Например, вкладка будет 0.86.channel.facebook.com. Вторая вкладка будет 1.86.channel.facebook.com. Насколько я понимаю, это решение для браузера ограничить 2 активных запроса в определенном домене. Как реализовано это решение для нескольких доменов?

Далее будут на сеансах чата. Разговоры чата будут разными для каждой вкладки? Как пользовательский интерфейс будет синхронизироваться с каждой вкладкой, как Facebook? Моя идея заключается в том, что за каждое действие сообщение отправляется пользователю собственного JID, содержащего действие, связанное с чатом. Например, открытие окна чата отправит строфу сообщения следующим образом:

<message from="my_own_jid" to="my_own_jid" type="chat">
    <body>{"jid-of-contact":"open-chat-box"}</body>
</message>

и это будет зависеть от клиента чата, и пользовательский интерфейс будет соответствующим образом скорректирован (в этом случае откроется окно чата для контакта).

Любые предложения/комментарии по этой реализации?

Спасибо!

Ответ 1

Я и моя команда работали над одной и той же проблемой - только мы используем Openfire вместо Ejabberd (в основном, потому что у нас есть навыки Java, но они не знакомы с Erlang). Наша компания создает браузерные версии.

Наше решение состоит из:

  • XMPPHP - для предварительной печати
  • Strophe.js - для сеанса связи (изменен)
  • Пенджаб - как диспетчер подключений (расширенный, измененный)
  • Openfire - как сервер XMPP

Мы используем punjab, потому что реализация OpenFire в BOSH не очень хорошо работала с другими компонентами.

В основном мы решили не создавать сеанс для каждой вкладки. Это связано с тем, что некоторые из наших игр работают так, как делают обычные сайты: щелчок по ссылке потребует полной новой страницы (тогда как новые игры полностью работают в ajax, и большая часть графического интерфейса остается неизменной). Другими словами: наш веб-чат должен работать в средах, где пользователь "перемещается по сайту". Один сеанс для одной вкладки будет означать новый сеанс для каждого запроса страницы, который кажется огромным накладным расходами, потому что игроки часто нажимают довольно быстро. Итак - мы хотели создать один сеанс и придерживаться игрока.

Чтобы решить, что мы - как вы - модифицировали strophe.js, чтобы прочитать/сохранить RID в файле cookie, чтобы все вкладки знали текущий RID и увеличивали его до правильного значения. Другое дело, мы сделали Strophe добавить CID в тело XMPP-строф. CID, как идентификатор клиента. Я скоро объясню использование.

Затем план состоял в том, чтобы изменить две вещи в punjab. Сначала мы добавили класс, который заменил обычный способ ожидания ожидающих запросов в punjab. Ожидание запросов BOSH теперь сохраняется в словаре с CID (который в настоящее время добавляет strophe.js в тело каждого запроса). Когда другой запрос с той же вкладки поступает в punjab, тогда он знает, на какой ожидающий запрос отправить пустой ответ. Если есть новые строфы, которые будут доставлены, punjab отправит их всем запросам ожидания в словаре. Таким образом, входящее сообщение распространяется на все вкладки. Во-вторых, мы добавили несколько строк, так что сообщение, отправленное с одной вкладки, сразу же отправляется обратно на все остальные вкладки. Таким образом, сообщение может появиться и в истории других вкладок.

Конечно, есть другие проблемы, с которыми приходится сталкиваться, например, не потерять историю чата в графическом интерфейсе, когда игрок переходит к следующему экрану. Хранение этого в cookie было бы плохо, поскольку все эти материалы отправляются с каждым запросом и вызывают много трафика. Для этого мы думаем о реализации чего-то, что похоже на архивирование сообщений XEP-0136.

Итак, чтобы сказать это, нам пришлось иметь дело с исправлением/расширением strophe.js и punjab, и мы немного модифицируем стандарты. Но сейчас это работает отлично, и я очень рад видеть, как эта настройка будет работать в бета-версии.

Ответ 2

Мое решение:

Каждая вкладка имеет свое собственное соединение на другом ресурсе, все с приоритетом 1.

В openfire добавить переменную сервера route.all-resources: true
Сообщения будут передаваться всем ресурсам.