Как равномерно распределить дилеров (настольных игр) по серверам?

В настоящее время я работаю над карточной онлайн-игрой, похожей на блэкджек, которая будет состоять из серии столов, где на каждом столе есть «дилер» и несколько игроков-людей. Дилер (компьютерный бот) отвечает за раздачу и тасование карт. Таблицы будут храниться в таблице базы данных PostgreSQL, и администратор сможет добавлять / удалять / редактировать таблицы.

Игра будет состоять из веб-интерфейса и серверной части REST / websocket API. Я, вероятно, буду использовать Kubernetes и Nginx в качестве балансировщика нагрузки для внутренних серверов.

На мой вопрос. Скажем, у меня есть один сервер, я мог бы просто заставить его читать список таблиц из базы данных и запускать процесс / поток дилера для каждой таблицы. Однако, если у меня есть 2 или более серверов, все становится более беспорядочным.

Как обеспечить сбалансированное назначение таблиц на всех серверах (например, если имеется 10 таблиц и 3 сервера, распределение должно быть примерно 3–3–4)?

Как я могу гарантировать, что в случае отказа сервера его таблицы будут переназначены действующему серверу?

Как убедиться, что при подключении нового сервера к сети некоторые существующие таблицы переназначаются ему, чтобы снизить нагрузку на другие серверы?


person Olivier Lalonde    schedule 10.08.2019    source источник


Ответы (1)


Я предполагаю, что каждое изменение состояния пересылается игрокам через веб-сокеты и сохраняется в базе данных для сохранения (только для восстановления после сбоя и некоторой статистики). Поэтому, если по какой-то причине server1 перестает работать и nginx начинает подключать клиентов table1 к server2, тогда у него (server2) не будет проблем с получением состояния игры, которая обслуживалась server1 до сбоя.

Вы можете использовать хэш URI или параметр для пересылки всех запросов, связанных с одной и той же таблицей, на конкретный сервер.

Когда nginx видит, что сервер отключен, он перестанет использовать его в качестве члена пула и последовательно перенесет все запросы на другой сервер.

Конечно, когда новый сервер подключается к сети, существующая таблица НЕ будет переназначена новому серверу во время игры (потому что вам нужно поддерживать соединение с веб-сокетом в рабочем состоянии).

Но когда игра заканчивается, вы можете сказать клиентам (через существующее соединение с веб-сокетом) повторно открыть новое подключение к веб-сокету со слегка измененным URL-адресом, что вынудит nginx повторно сбалансировать соединения между серверами.

upstream backend {
    hash $request_uri consistent;
#    hash $arg_table consistent;
    server bj-1.card-games.com max_fails=2 fail_timeout=2s;
    server bj-2.card-games.com max_fails=2 fail_timeout=2s;
    server bj-3.card-games.com max_fails=2 fail_timeout=2s;
}

server {
 location / {
  proxy_pass http://$backend;
 }
}
person Maxim Sagaydachny    schedule 27.11.2019