Как стать автором
Обновить

Комментарии 22

[sarcasm]
Ждем статью: разница между Vanila JS и Jquery
[/sarcasm]

Любопытно… То есть вы считаете что JS vs jQuery — это тривиальная тема и не стоит статьи? Или вы имеете в виду что их и так много?

По поводу SocketIO мне в свое время не было достаточно информации. Ни документация ни SO не могли мне помочь в моих вопросах. Мне кажется эта библиотека достаточно удобна чтобы еще одна статья хотя бы напомнила о ней.
Предположу, что ThisMan имеет в виду, что сравнивается теплое и мягкое. Ну или кирпич vs кирпичное здание.
Спасибо за перевод.

Вообще говоря, аргументы против SocketIO не очень убедительны в плане размера. Минифицированный js файлик у меня весит 51 Кбайт, что как бы в 4 раза меньше заявленных 207 Кбайт. Тем более загружается он один раз же, а потом из кэша берется. Черт, да сейчас favicon для сайтов могут больше весить!

Честно говоря, настроить SocketIO через nginx для Flask для вебсокетов у меня получилось не с первого раза (и даже не с третьего), но мне понравился его fallback на AJAX при проблемах с вебсокетами, а уж автоматическое восстановления соединения — это еще одна киллер-фича.

На бэкенде он удобно используется. Мне нужны были именно broadcast-рассылки и отлично оно работает. При рефакторинге проекта попробовал переписать на Django-channels (вебсокеты) и сильно обжегся, когда осознал что там даже список клиентов не получить, не говоря уж о броадкасте.

Fallback на ajax практически не нужен ни при каких обстоятельствах. Т.к. те браузеры которые не поддерживают сокеты — они же не поддерживают и ajax в современном понимание (в основном это opera mini и старіе версии IE).


Сама по себе библиотека socket.io имеет два кардинальных недостатка для широкого использования в высоконагруженных приложения.
1) Запуск socket.io на сервере например на node.js или на любом другом очень быстро приводит к исчерпанию ресурсов системы т.к. каждое соединение к серверу, даже если нет интенсивного обмена данными создае большую нагрузку на систему.
2) socket.io не гарантирует доставку всех сообщений. Поэтому для реально работающих приложений — чатов и т.п. приходится допиливать некоторую логику по доставке пропущенных сообщений (сообщения могут теряться в процессе разрыва и восстановления соединения) и дублирующих сообщений (это оборотная сторона доставки пропущенных сообщений)


Выход — применение специализированных серверов и протоколов для связи по сокетам (например mqtt, centrifugo)

Если веб приложение может работать только через HTTPS (корпоративные пользователи), то как выйти из этой ситуации при работе через веб-сокеты?
У меня нет опыта работы через socket.io, но от сокетов пришлось отказаться, клиенты отказывались открывать нестандартный порт.

Вебсокеты могут работать на порту 443. И любом другом. При этом различитььвеб сокеты и чистый https невозможно. Если вебсокеты работают на другом сервере чем сайт например на mqtt сервере, то его можно или через nginx проксировать на определенный урл или же поднять на субдомене. Второй вариант лучше так как nginx конечно может держать много коннектов но значительно меньше чем mqtt сервер на erlang

Эта проблема легко решается переносом веб-сокет сервера за ngnix reverse proxy. Например, веб-сокет сервер на host:8888 мапится на host:443/websocket.
Поэтому для реально работающих приложений — чатов и т.п. приходится допиливать некоторую логику по доставке пропущенных сообщений (сообщения могут теряться в процессе разрыва и восстановления соединения)

Да, и очень часто бизнес логика напрямую завязана на состояние коннекшна. Например показать юзеру его пинг, или показать в чате, что игрок реконнетится. На сервере для реконнектов нужно контролировать тайманты на сессию, а также уметь жестко дисконнектить клиента. А еще нужно уметь настраивать коннекшн на более низком уровне (tcp_nodelay, keep_alive, send/receive buffer, etc...), защищаться от разного рода атак на ресурсы, напр. контролировать количество коннектов на клиента, или организовывать delay-пулы против overload-а. Все это становится недоступно при использовании абстрактных надстроек более высокого уровня.

Есть определенный класс приложений где гарантированная доставка не нужна. То есть если клиент отвалился то он уже вне игры. Для таких приложений натив больше подходит. Но остается другое ограничение — масштабируемость. Пожалуй любые из известных серверов кроме erlang падают при 10...100 тысячах одновременных коннектов. Специализированные серверы могут выдерживать нагрузки на пару порядков выше.

Есть другая либа SockJS, которая эмулирует вебсокет с разными транспортами. В отличие от socket.io, заточена под разные бэкенды. Для джавистов есть Atmosphere Framework, который я пробовал юзать.


Тем не менее на реальном проде использование транспортных врапперов отнюдь не так хорошо, как кажется — вылезают такие кейсы, которые и не снились. Требуется спуск на уровень на транспортный уровень, который вы уже не контролируете, либо библиотека недостаточно гибкая, чтобы покрыть этот кейс. Особенно актуально на мобильной связи. Поэтому, начиная с какого-то момента, требуется разработка собственного протокола с использованием голого вебсокета или лонгполлинга.

Такие протоколы были разработаны уже дано — mqtt — один из них.

Всегда проще написать свой велосипед, понятный и заточенный под конкретную задачу, чем разбираться в абстрактном мультифункциональном протоколе, ломать голову как с помощью него реализовать необходимое, бороться с ограничениями в дизайне, а затем на проде ловить лютый гемор по поводу неучтенных нюансов в поведении провайдера и низлежащих протоколов.

Протокол mqtt очень продуман и разработан хорошими специалистами из ibm. Он прост и строг. Нацелен на гарантированную доставку сообщений, в этом его основная функция. Все знакомые мне попытки реализовать аналогичное поверх socket.io или наличных сокетов очень быстро превращались в трэш из за изначальной непродуманности как раз этого момента. Когда внезапно оказывается что соединение может рваться а сообщения теряться или дублироваться.

А есть еще специально форк, но теперь уже самостоятельный проект — engine.io и также для разных языков и бекендов.

Насколько я помню, штука с несколькими запросами фикситься переставлянием вебсокета как первого протокола. Изначально, ws не был везде по дефолту, и поэтому лучше было быстрее показать юзеру первые данные, а потом переключиться по возможности
207 КБ это много? Видимо, именно поэтому многие сайты сейчас грузят целые мегабайты *пожатого* жс…
Веб-сокеты и Socket.IO, вероятно, являются двумя наиболее распространенными средствами коммуникации в режиме реального времени (далее — живое общение). Но чем они отличаются?

… Веб-сокеты и Socket.IO являются самыми популярными средствами живого общения в современном вебе. Какое из них выбрать? В чем разница между этими технологиями?


зачем повторяться?

Не понял зачем столько телодвижений, если можно указать что бы socket.io как клиент так и сервер юзали только websocket без всяких там поллингов, просто добавлением конфига? Да и размер второй версии для клиента ~20kb, а на серваке пофиг… ниче не понимаю.

Сравнение сокета с ее же оберткой? :/

For instance, think about broadcasting a message to every connected client: with Socket.IO is just one method (.broadcast), but in vanilla WebSockets you’ll have to implement it on your own, so you’ll have to rethink about the way it works.


О боже как трудно написать проход по массиву клиентов =))

Автор вроде синьер… статья для начинающих в вебе?

Прошу прощения, но:


1)


Если говорить о сетевом трафике, то веб-сокеты отправляют всего два запроса:
GET для получения HTML страницы
UPGRADE для соединения с веб-сокетами

Вебсокеты отправляют ровно один запрос — GET с заголовками Connection: Upgrade и Upgrade: websocket (который Вы, видимо, назвали UPGRADE). А первый GET который Вы упомянули не имеет никакого отношения к установлению вебсокет соединения (как например и куча другий GET запросов где загружаются картинки, CSS и прочие ресурсы).


2)


Ну, если вы открываете соединение на «server 1», затем балансировщик переключает вас на «server 2», вы получите ошибку: «Error during WebSocket handshake: Unexpected response code: 400». Socket.IO решает эту проблему с помощью cookie (или с помощью маршрутизации соединений на основе исходных адресов), а у веб-сокетов не существует подобного механизма.

Вебсокет соединение открывается за 1 HTTP запрос, как балансировщик может сделать переключение на другой сервер посреди запроса? "Это какой-то неправильный балансировщик", как говорил Винни Пух, "и он неправильно балансирует".


С другой стороны если Вы делаете горизонтальное масштабирование через балансировщик HTTP запросов, то в настройке балансировщика должны быть правила "приклеивания" запросов клиента к определенному серверу на основе определенных правил (каких именно — зависит от специфики проекта и возможностей балансировщика). Если Вы это не настраиваете на балансировщике — то плохо открывающиеся вебсокеты — это будет далеко не главная проблема в Вашем проекте.

Ну не знаю. Использовать липкие сессии не кажется надежным решением. Уж лучше сразу настраивать кластер.

НЛО прилетело и опубликовало эту надпись здесь
Socket.IO работает с собственной библиотекой и его нельзя использовать в целях, не связанных с веб-разработкой.

Существует библиотека Socket.IO-client для node.js, позволяющая реализовать
P2P коммуникация, обмен данными между серверами в режиме реального времени и т.д.

с использованием socket.io.
Понимаю, что это не туториал, но все равно внесу поправку относительно метода broadcast.
Возможно пример кода взят из старой версии, но сейчас вместо метода broadcast можно применить метод emit к самому серверу
const io = require('socket.io')(3002);

io.on("connection", socket => {
    socket.on('message', message => {
       io.emit(`[${socket.id}]: ${message}`);
    });
});

Зарегистрируйтесь на Хабре, чтобы оставить комментарий

Публикации

Истории