0

我目前正在开发一款类似于二十一点的在线纸牌游戏,它将由一系列桌子组成,每张桌子都有一个“经销商”和多个人类玩家。庄家(计算机机器人)负责发牌和洗牌。这些将存储在 PostgreSQL 数据库表中,并且人类管理员可以添加/删除/编辑表。

游戏将包含一个 Web 前端和一个 REST/websocket API 后端。我可能会使用 Kubernetes 和 Nginx 作为后端服务器的负载均衡器。

到我的问题上。假设我有一个服务器,我可以简单地让它从数据库中读取表列表并为每个表启动一个经销商进程/线程。但是,如果我有 2 台或更多服务器,事情就会变得更加混乱。

如何确保在所有服务器上以平衡的方式分配(例如,如果有 10 个表和 3 个服务器,则分布应大致为 3-3-4)?

如何确保如果服务器出现故障,其会重新分配给实时服务器?

我如何确保当新服务器上线时,一些现有的被重新分配给它,以减少其他服务器的工作量?

4

1 回答 1

0

我假设每个状态更改都通过 websockets 转发给玩家并存储到数据库中以进行持久性(仅用于故障恢复和一些统计信息)。因此,如果由于某种原因 server1 停止工作并且 nginx 开始将 table1 的客户端连接到 server2,那么它(server2)在获取失败之前由 server1 服务的游戏状态时将没有问题。

您可以使用 URI 或参数的哈希将与同一表相关的所有请求转发到特定服务器。

当 nginx 看到该服务器下线时,它将停止将其用作池成员并以一致的方式将所有请求迁移到另一台服务器。

当然,当新服务器上线时,游戏过程中不会将现有表重新分配给新服务器(因为您需要保持 websocket 连接处于工作状态)。

但是当游戏结束时,您可以告诉客户端(通过现有的 websocket 连接)通过稍微修改的 URL 重新打开新的 websocket 连接,从而迫使 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;
 }
}
于 2019-11-27T18:14:44.077 回答