Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Comet-сервер своими руками

Comet-сервер своими руками

Мой и Макса Лапшина доклад на Highload++ 2012.

Dmitry Demeshchuk

October 24, 2012
Tweet

More Decks by Dmitry Demeshchuk

Other Decks in Programming

Transcript

  1. Возможные реализации • Периодические запросы на сервер • Comet: •

    Long polling • Websockets • Server Sent Events • Прочее гуано (Flash sockets)
  2. • Не требует немедленного ответа • Совместим с keepalive •

    Моментальное обновление • Много одновременных подключений • Требуется переподключение Long-polling
  3. • Постоянное соединение • Намного быстрее, чем HTTP • Не

    везде поддерживаются • Еще не устоялись как стандарт
  4. • CGI - ~1000-2000 • Apache - 1000-5000 • Node.JS

    - 1000000 (?) • Erlang - 2277845 Лимит одновременных подключений
  5. Хранение внутреннего состояния • MySQL — надежно и очень медленно

    • Redis/memcached — ненадежно и медленно • Внутри VM — быстро и опасно • Репликация
  6. Нет решений для распределенного комета из коробки • Redis -

    master-slave репликация • Memcached - нет сообщений • Postgres - медленно и без репликации
  7. Почему Erlang • Феноменальная для веба производительность • Феноменальная для

    веба многоядерность • Распределенность из коробки • Асинхронный IO в последовательном виде • Изоляция данных • Горячее обновление кода
  8. Желаемые фичи • In-memory • История сообщений в канале •

    Горячий бэкап нод • Zero-conf, no-ops сервер
  9. Хроника событий 1. Реализация pub/sub-механизма 2. Написание тестов 3. Прикручивание

    веб-сервера 4. Доработка напильником 5. Бенчмарки 6. ... 7. PROFIT!
  10. • Распределенный • Автоматический failover • Написан за 2.5 часа

    • Меньше 300 строк кода • Один race condition • Один баг-опечатка Первый рабочий pub/sub
  11. Тесты • Выявили race condition • Очень помогли в дальнейшей

    разработке • Отняли несколько часов • Покрыли примерно 80% кода pub/sub-части • По размеру сравнимы с кодом
  12. Попытка №1 • Amazon EC2 large instances • 1000 клиентских

    подключений • 1 rps с каждого клиента
  13. • 20-140% CPU на одной машине • 2000 deliveries per

    second Мы посовещались и решили, что Amazon не очень
  14. Выходы* • Таймаут на клиенте • Таймаут на сервере •

    Пользовательские сессии * лучше - в комбинации
  15. • Клиент шлет сообщение в полную очередь • Отваливается с

    таймаутом • Перепосылает в ещё более полную очередь • OOM Killer In Da House Замкнутый круг
  16. • Перед публикацией проверяем длину очередей • Если большая, шлем

    HTTP 429 • Клиент сам перепошлет завтра позже Power of Erlang
  17. Неплохая производительность: WhatsApp - ~11500 pps DPS - ~7500 pps

    Функциональность и железо разные, но порядок цифр похожий.
  18. Важные моменты • Не следует хранить всю историю в памяти

    • Следите, какие процессы перегружаются • Избегайте избыточных сообщений • Не делайте запросы слишком часто • Используйте пользовательские сессии • Старайтесь не гонять лишние данные
  19. Технические компромиссы могут заметно ускорить работу сервера. • Не хранить

    очереди • Терять сообщения • Отказаться от сессий (в некоторых случаях) • Посылать все в /dev/null