GraniteDS 和异步 Servlet
据我所知,GraniteDS 是唯一为实时消息传递实现异步 servlet 的解决方案,即。数据推送。此功能不仅适用于 Servlet 3 容器(Tomcat 7、JBoss 7、Jetty 8、GlassFish 3 等),而且适用于旧的或其他具有特定异步支持的容器(例如 Tomcat 6/CometProcessor、WebLogic 9+/AbstractAsyncServlet , ETC。)
其他解决方案没有此功能 (BlazeDS) 或使用 RTMP(LCDS、WebORB 和 Clear Toolkit 的最新版本)。关于 RTMP 实现我不能说太多,但 BlazeDS 显然缺少可扩展的实时消息传递实现,因为它只使用同步 servlet 模型。
如果您需要处理成千上万的并发用户,您甚至可以创建一个 GraniteDS 服务器集群,以进一步提高可扩展性和稳健性(例如,请参阅此视频)。
异步 Servlet 性能
异步 servlet 与经典 servlet 的可扩展性已经过多次基准测试,并给出了令人印象深刻的结果。例如,请参阅Jetty 博客上的这篇文章:
对于非 NIO 或非基于 Continuation 的服务器,这将需要大约 11,000 个线程来处理 10,000 个并发用户。Jetty 只用 250 个线程处理这个数量的连接。
经典同步模型:
- 10,000 个并发用户 -> 11,000 个服务器线程。
- 1.1 比率。
Comet 异步模型:
- 10,000 个并发用户 -> 250 个服务器线程。
- 0.025 的比率。
这种比率可以从其他异步实现(不是 Jetty)中大致预期,并且使用 Flex/AMF3 代替纯文本 HTTP 请求不应该改变太多结果。
为什么选择异步 Servlet?
当立即处理每个请求时,经典(同步)servlet 模型是可以接受的:
request -> immediate processing -> response
数据推送的问题在于,HTTP 协议不存在真正的“数据推送”:服务器无法发起对客户端的调用以发送数据,它必须响应请求。这就是 Comet 实现依赖于不同模型的原因:
request -> wait for available data -> response
使用同步 servlet 处理,每个请求都由一个专用服务器线程处理。但是,在数据推送处理的上下文中,该线程大部分时间只是在等待可用数据,而在消耗大量服务器资源的同时什么也不做。
异步处理的全部目的是让 servlet 容器使用这些(通常)空闲线程来处理其他传入请求,这就是为什么当您的应用程序需要实时消息传递功能时,您可以期望在可伸缩性方面得到显着改进。
您可以在 Web 上找到许多其他资源来解释此机制,只需在 Comet 上搜索即可。