![Page 1: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/1.jpg)
Особенности применения Websocket
на примере работы в ERP Фролов Александр
14.06.2013г.
![Page 2: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/2.jpg)
Актуальность данных
• Данные на странице — устаревают;• основании устаревших данных можно принять не верное
решение;• Не верное решение ведёт в конечном счёте к финансовым
потерям, если это приложение решает бизнес задачи.• Выход? Нужно получать данные от сервера в момент их
поступления на сервер;• Нужно иметь возможность инициировать отправку
данных сервером.
![Page 3: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/3.jpg)
Как быть, каким способом актуализировать данные?
• Первый тривиальный способ — запрашивать каждые n секунд сервер о новых данных. При этом чем чаще — тем быстрее получаем обновление данных.
• Простой подсчёт показывает: в ERP системе за сутки будет генерировать 2,5 миллиона запросов. КПД от работы системы — стремится к нулю.
![Page 4: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/4.jpg)
Ограничения: согласно спецификации HTTP 1.1
браузер не должен иметь более двух соединений одновременно
• Если открыто более двух страниц в браузере очень вероятны случаи, когда запросы на обновление не проходят;
• Применение других способов, отличных от простых запросов на обновления так же требует учитывать это обстоятельство;
![Page 5: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/5.jpg)
Comet (программирование)
• Модели работы веб приложений, при которых постоянное HTTP соединение позволяет веб-серверу отправлять (push) данные браузеру без дополнительного запроса со стороны браузера, называют Comet технологиями, а приложения, которые реализуют такую модель — comet приложениями.
• Благодаря comet-приложениям клиент в режиме реального времени может взаимодействовать с сервером, опираясь на постоянное или long polling соединение HTTP.
![Page 6: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/6.jpg)
Реализации comet технологий
• Потоковые: открывается постоянное соединение между клиентом и сервером.
• Long polling (длительное соединения): открывается соединение и ожидается ответ по таймауту или до таймаута, после чего соединение переоткрывается
![Page 7: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/7.jpg)
Потоковые: открывается постоянное соединение между клиентом и
сервером.
Скрытый IFRAMEПостоянно в IFRAME шлются данные, например, строки с
пустым комментарием, и в нужный момент сервер передает javascript строку, которая сразу выполняется. Из минусов можно выделить не возможность нормальной обработки ошибок и не возможность отследить реакцию на передачу данных со стороны сервера.
![Page 8: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/8.jpg)
XMLHttpRequest
У ряда браузеров (FF, WebKit, IE10) имеется возможность получать multipart response — ответ порциями, тем самым очередную порцию отсылаем тогда, когда нужно серверу. Особого распространения не получило.
![Page 9: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/9.jpg)
Ajax с long polling
Браузер делает Ajax запрос на сервер, который остается открытым, пока сервер не отправит данные. По таймауту пересоздается соединение.
![Page 10: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/10.jpg)
Script tag long polling
Подгружается динамически javascript файлы, в которых передаются данные по мере их поступления. Как только один файл «загрузился», подгружается следующий файл.
![Page 11: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/11.jpg)
WebSocket
WebSocket - веб-технология, обеспечивает полнодуплексный канал связи через одно соединение TCP. Протокол WebSocket был стандартизирован IETF RFC 6455 в 2011 году. WebSocket соответствует стандартам W3C.
![Page 12: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/12.jpg)
Базовое использование WebSocket на стороне клиента:
<script>
ws = new WebSocket("ws://site.com/ws");
// обработка события, при установки соединения
ws.onopen = function() { alert("Connection opened...") };
// обработка события, при закрытии соединения
ws.onclose = function() { alert("Connection closed...") };
// обработка события получения сообщение через веб-сокет
ws.onmessage = function(e) { alert(e.data); };
</script>
![Page 13: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/13.jpg)
Немного деталей :)
Процесс открытия WS выглядит на данный момент следующим образом.
![Page 14: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/14.jpg)
В начале идёт HTTP-запрос:
GET /ws HTTP/1.1
Host: site.com
Upgrade: websocket
Connection: Upgrade
Sec-WebSocket-Key: x3JJHMbDL1EzLkh9GBhXDw==
Sec-WebSocket-Protocol: chat
Sec-WebSocket-Version: 13
Origin: http://site.com
![Page 15: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/15.jpg)
Если сервер поддерживает WS, то то ответ будет:
HTTP/1.1 101 Switching ProtocolsUpgrade: websocketConnection: UpgradeSec-WebSocket-Accept:
HSmrc0sMlYUkAGmm5OPpG2HaGWk=Sec-WebSocket-Protocol: chat
![Page 16: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/16.jpg)
Sec-WebSocket-Key содержит случайное значение,закодированное Base64.
Sec-WebSocket-Accept вычисляется путём конкатенации Sec-WebSocket-Key и «magic string»:
258EAFA5-E914-47DA-95CA-C5AB0DC85B11
$SecWebSocketAccept = base64_encode(sha1($SecWebSocketKey . '258EAFA5-E914-47DA-95CA-C5AB0DC85B11', true));
Существует две модификации протокола: ws:// и wss://, это по смыслу почти как http:// и https://, то есть wss:// - шифрованное соединение.
![Page 17: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/17.jpg)
Формат передаваемых текстовых данных
0x00 <строка в кодировке UTF-8> 0xFF
просто строка текста — последовательность байт, к которой спереди приставлен нулевой байт 0x00, а в конце — 0xFF. И все — никаких заголовков, метаданных.
![Page 18: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/18.jpg)
Передача и бинарных данных
Длина записывается по следующим правилам: Каждый байт в указании длины рассматривается по частям: самый старший бит указывает является ли этот байт последним (0) либо же за ним есть другие (1), а младшие 7 битов содержат собственно данные.
0x80 <длина - один или несколько байт>
<тело сообщения>
1 0 0 0 1 1 1 01 0 0 0 0 1 1 0 0 0 0 1 0 1 1 0
![Page 19: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/19.jpg)
Какими браузерами поддерживается?
Protocol IE FF FF(android)
Chrome Safari Opera
hixie-75 4 5.0.0
hixie-76hybi-00
4 6 5.0.1 11
7 hybi-07 6
8 hybi-10 7 7 14
13 RFC 6455 10 11 11 16 6 12.10
![Page 20: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/20.jpg)
Организации работы WS
Различные реализации серверов на многих платформах: node.js, Pyton, Ruby on Rails, PHP...
Из PHP Open Source проектов можно отметить довольно динамично развивающийся проект phpDeamon. Но это универсальный всеядный комбайн.
Но в реальности используем более легкую реализацию, которую проще проверить и адаптировать под свои нужды.(https://github.com/lemmingzshadow/php-websocket)
![Page 21: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/21.jpg)
Принцип работы WS сервера на php
- запуск в цикле опроса открытых портов.
while(true) {
foreach($sockets as $socket) {
// read socket
$data = readBuffer($socket);
process_data($cleint[(int)$socket], $data);
}
}
![Page 22: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/22.jpg)
Обычная схема работы
БДWSК
![Page 23: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/23.jpg)
Схема быстрого внедрения WS
БД
WS
К2
Кn
К1
WSS
Ajax
mess
mess
mess
mess
Mess — сообщение Об изменениях, для всех одно и тоже, фильтрация «нужен / не нужен» или на сторонеклиента или решение обОтправки mess принимаетWSS исходя из типа страницы на строне клиента.
![Page 24: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/24.jpg)
Продвинутая схема использования WS
БД
WS
К2
Кn
К1
WSS
Ajax
mess
mn
m2
m1
mess — сообщение об измененияхM1, M2, … Mn — подготовленные для каждого типа страниц сообщения, включающие все специфические данные. Не достающие данные добираются из БД.
![Page 25: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/25.jpg)
Полная интеграция WS
БД
WS
К2
Кn
К1
WSS
HTTP
m0
mn
m2
m1
![Page 26: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/26.jpg)
Конкурирующие запросы• С ростом количества запросов может быть ситуация,
когда данные более свежего запроса придут позже, чем данные более старого запроса.
• Необходимо посылать с данными на изменения временные метки, чтобы обеспечить минимальную защиту от подобных коллизий;
• Так же нужна временная метка о начале работы с данными, то есть когда пришли данные, которые отредактировали;
• Две временные метки позволяют сравнить данные, которые меняем с данными которые находятся в БД, а так же их «свежесть» и в случае чего не допустить перезатирания новых данных — старыми. При этом клиенту, приславшего конфликтный запрос — отправлять уведомление с просьбой проверки данных + обновленные данные.
![Page 27: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/27.jpg)
Стоит ли использовать более серьёзный подход?
• Можно использовать систему разделения ресурсов, флаги, семафоры...
• Внедрение связано со значительным усложнением всей системы;
• От пользователе потребуются дополнительные усилия в работе;
• Необходимо четко очень реальную необходимость внедрения.
![Page 28: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/28.jpg)
Пишите логи
В обязательном порядке записываете в логах обо всех изменениях в системе: • кто• когда• что• старое значение• новое значение
![Page 29: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/29.jpg)
Собирайте мусор в WSS
WSS представляет собой один работающий процесс по приему, обработке и отправке сообщений. Со временем не используемые переменные постепенно забивают память вплоть максимально возможного лимита для php процесса. Чтобы этого не случилось необходимо подчищать за собой переменные и объекты (gc_enble(); gc_collect_cycles(); gc_disable; )
![Page 30: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/30.jpg)
Перегружайте WSS иногда :)
gc_collect_cycles() помогает, но объем используемой памяти всё равно может неуклонно расти.
Поэтому проверяйте объём используемой памяти, и в случае превышения определенного лимита инициируйте перезагрузку WSS.
![Page 31: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/31.jpg)
Пример упрощенного кода ядра WSS
$flag = true;While ($flag) { If (time() - $time_last_check >= 60 сек) { If (get_file_flag() == 1) { $flag = false; } else if (memory_get_peak_usage()/1024/1024
>= ini_get("memory_limit") * 0.8) { send_notice(); set_timer_to_reboot(); $flag = false(); } }}
![Page 32: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/32.jpg)
Возможности «виртуального» кэша
• Так как процесс обрабатывающий сообщения один, то и сохраняя данные в определенный массив/объект можно получить нечто на подобие кэша с актуальными данными;
• Следует учитывать ограничения на объём памяти и не забывать подчищать такой кэш.
• Определив экспериментальным путем суточные потребности ERP системы были увеличены лимиты с 128Мб, до 1Гб памяти для WSS, тем самым все необходимые для работы данные в результате находились в кэше.
• В PHP 5.3.0 можно указывать в php.ini memory_limit 1G
![Page 33: DevConf2013: Особенности применения WebSocket на примере работы в ERP системе](https://reader034.vdocuments.pub/reader034/viewer/2022051413/554bc7d6b4c90530298b56b4/html5/thumbnails/33.jpg)
Ссылки на ресурсы, статьи, GitHub
http://en.wikipedia.org/wiki/Comet_(programming)http://en.wikipedia.org/wiki/WebSockethttps://github.com/nicokaiser/php-websockethttp://nginx.com/news/nginx-websockets.htmlhttps://github.com/disconnect/apache-websocket https://github.com/kakserpom/phpdaemon https://github.com/nicokaiser/php-websocket https://github.com/hoaproject/Websocket https://github.com/lemmingzshadow/php-websocket