发布/订阅服务器的可扩展性问题是什么?

发布/订阅服务器的可扩展性问题是什么?

我正在研究使用 websockets 设置发布/订阅服务。据我所知,可扩展性瓶颈主要在于内存,这会影响一次可以打开多少个套接字,因此我认为将其与运行 API 等服务的其他服务器分开是明智之举。这是正确的吗?我认为在托管方面,内存比计算能力更昂贵,那么在优化此类服务器的可扩展性和成本方面,是否有任何最佳实践?

目标是在现场系统签入新数据时为该 Web 应用程序的用户提供实时更新,而无需定期轮询后端。但我们不想将服务器成本翻倍,否则可能不值得。我们正在使用具有负载平衡和自动扩展功能的 AWS EC2 来处理当前的 API 服务器。

答案1

单个插槽的实际内存使用量并不是那么多。

消耗内存的是与哪个客户端对哪些更新感兴趣以及哪个客户端已经收到特定更新相关的状态。

在原始实现中(即使用 OS 网络堆栈),后一种状态以传出缓冲区的形式保存 - 因此,如果将更新发送到 10,000 个客户端,则数据将被复制 10,000 次,每个副本都会附加到传出队列,并在其中添加必要的标头(包含每个连接的状态),然后为硬件构建一个描述符,指示它发送由标头和有效负载连接而成的数据包。

每个客户端的有效负载副本都会保留在内存中,直到客户端确认为止,这就是内存需求的来源。这些内存无法调出,因此会给其他应用程序带来内存和缓存压力。

有一些实现在服务器程序内部实现了部分网络堆栈,这些可以通过引用计数或按需重新创建有效负载来避免复制,这使您可以减少内存使用量,但涉及大量棘手的编码才能真正实现可扩展性,尤其是多插槽服务器在那里提出了一些有趣的问题,操作系统网络堆栈已经知道如何解决这些问题。

您拥有的选择

  1. 在与应用程序相同的服务器上运行发布/订阅服务
  2. 在具有 OS 网络的专用服务器上运行发布/订阅服务
  3. 在具有自定义网络的专用服务器上运行发布/订阅服务
  4. 在多个专用服务器上运行发布/订阅服务

是服务增长过程中的升级策略。从共享到专用不需要太多规划,可以根据需要进行;一旦完成,就该准备后续阶段了。

扩展到多台服务器将会给您的系统引入不确定性,因为客户端可能会以不同的顺序接收更新,因此为了使此扩展步骤成功,您的客户端需要意识到这一点并能够呈现一致的视图 - 这是否简单或困难取决于您的实际应用。

总结:无需过早优化。拆分服务,以便第一步扩展是简单的配置更改,并在发生此情况后立即开始优化。

相关内容