Ключевые концепции

Понимание основных концепций Localzet Cluster необходимо для эффективной разработки распределенных приложений.

Gateway-Worker архитектура

Cluster использует архитектуру Gateway-Worker для разделения ответственности:

  • Gateway: Обрабатывает клиентские соединения, не содержит бизнес-логику
  • Business Worker: Обрабатывает бизнес-логику, не имеет прямых соединений с клиентами
  • Register: Координирует компоненты и обеспечивает service discovery

Преимущества:

  • Легкое горизонтальное масштабирование
  • Разделение ответственности
  • Высокая производительность

client_id

Каждое клиентское соединение получает уникальный client_id - глобальный идентификатор по всему кластеру.

Формат: 20-символьная hex-строка (например: 00000000000000000001)

Характеристики:

  • Глобально уникальный в рамках кластера
  • Не меняется в течение жизни соединения
  • Используется для всех операций с клиентом
  • Формируется из: Gateway IP, Gateway Port, Connection ID

Использование:

// Отправить сообщение клиенту
Gateway::sendToClient($client_id, $message);

// Получить сессию
$session = Gateway::getSession($client_id);

// Закрыть клиента
Gateway::closeClient($client_id);

Группы (Groups)

Группы позволяют объединять клиентов для массовой рассылки сообщений.

Использование:

// Добавить клиента в группу
Gateway::joinGroup($client_id, 'chat_room_1');

// Отправить сообщение группе
Gateway::sendToGroup('chat_room_1', $message);

// Удалить из группы
Gateway::leaveGroup($client_id, 'chat_room_1');

// Распустить группу
Gateway::ungroup('chat_room_1');

Особенности:

  • Клиент может быть в нескольких группах одновременно
  • Группы автоматически очищаются при отключении клиента
  • Идеально для комнат чата, каналов, игровых сессий

UID (User ID)

UID позволяет привязать client_id к идентификатору пользователя.

Преимущества:

  • Один пользователь может иметь несколько соединений (несколько устройств)
  • Отправка сообщений по UID отправляется на все устройства пользователя
  • Не нужно хранить маппинг client_id -> user_id

Использование:

// Привязать после аутентификации
Gateway::bindUid($client_id, $user_id);

// Отправить сообщение пользователю (всем его устройствам)
Gateway::sendToUid($user_id, $message);

// Проверить онлайн статус
$isOnline = Gateway::isUidOnline($user_id);

// Получить все соединения пользователя
$client_ids = Gateway::getClientIdByUid($user_id);

Важно:

  • При отключении client_id автоматически отвязывается от UID
  • Если пользователь зайдет с нового устройства, нужно снова вызвать bindUid

Сессии (Sessions)

Сессии позволяют хранить данные, связанные с клиентским соединением.

Характеристики:

  • Автоматически загружаются в $_SESSION при обработке события
  • Автоматически сохраняются после обработки события
  • Доступны только в контексте обработки события в Business Worker

Использование:

public static function onMessage($client_id, $message)
{
    // Сессия уже загружена
    $userId = $_SESSION['user_id'] ?? null;
    
    // Чтение
    $lastVisit = $_SESSION['last_visit'] ?? null;
    
    // Запись
    $_SESSION['last_visit'] = time();
    $_SESSION['message_count'] = ($_SESSION['message_count'] ?? 0) + 1;
    
    // Автоматически сохранится после обработки
}

// Извне (Client API)
Gateway::setSession($client_id, ['key' => 'value']);
Gateway::updateSession($client_id, ['new_key' => 'value']);
$session = Gateway::getSession($client_id);

Роутинг

Gateway маршрутизирует сообщения от клиентов к Business Worker'ам.

Алгоритмы роутинга:

  1. routerBind (по умолчанию):

    • При первом сообщении выбирается случайный Business Worker
    • Все последующие сообщения идут к тому же Worker
    • Гарантирует сохранение контекста сессии
  2. routerRand:

    • Каждое сообщение отправляется случайному Worker
    • Равномерное распределение нагрузки
    • Не гарантирует сохранение контекста между сообщениями
  3. Пользовательский роутер:

    • Можно реализовать свою логику роутинга
    • Например, по типу сообщения, по load balancing и т.д.

Настройка:

// По умолчанию
$gateway->router = [Gateway::class, 'routerBind'];

// Случайная маршрутизация
$gateway->router = [Gateway::class, 'routerRand'];

// Пользовательская функция
$gateway->router = function($server_connections, $client_connection, $cmd, $buffer) {
    // Вернуть TcpConnection к Business Worker
};

Service Discovery

Register обеспечивает автоматическое обнаружение сервисов.

Как это работает:

  1. Gateway запускается и регистрируется в Register
  2. Register хранит список всех Gateway адресов
  3. Business Worker подключается к Register и получает список Gateway
  4. Business Worker подключается ко всем Gateway для получения событий

Преимущества:

  • Автоматическое обнаружение новых Gateway
  • Автоматическое удаление недоступных Gateway
  • Не требует статической конфигурации

Производительность

Оптимизации:

  1. Бинарный протокол: Внутренний протокол между Gateway и Business Worker оптимизирован для скорости
  2. Параллельная обработка: Множество Business Worker процессов обрабатывают события параллельно
  3. Минимальные копии данных: Данные передаются напрямую без лишних копирований
  4. Кеширование: Gateway кеширует структуры данных для быстрого доступа

Рекомендации:

  • Используйте группы вместо отправки множеству клиентов по client_id
  • Используйте UID для пользовательских сообщений
  • Минимизируйте размер сессий
  • Используйте raw данные для больших объемов информации

Обработка ошибок

Типичные ошибки:

  1. Business Worker недоступен:

    • Gateway автоматически перестает маршрутизировать на него
    • Клиенты могут продолжить работу через другие Worker'ы
  2. Gateway недоступен:

    • Register удаляет его из списка
    • Клиенты должны переподключиться к другому Gateway
  3. Register недоступен:

    • Business Worker пытается переподключиться
    • Gateway пытается перерегистрироваться
    • Система автоматически восстанавливается

Мониторинг:

  • Используйте логи для отслеживания проблем
  • Настройте алерты на критические события
  • Мониторьте количество соединений и нагрузку