我正在编写一个基于socket.io的服务器,我正在努力避免厄运的金字塔,并保持低内存。我写信给这个客户-http://jsfiddle.net/QUDXU/1/我用CCD_ 1运行。因此,有1000个连接在不断发出请求。
对于服务器端,a尝试了3种不同的解决方案,我进行了测试。在我让一切运行一个小时后,服务器使用的RAM的结果是:
- 简单回调-http://jsfiddle.net/DcWmJ/-11200万
- Q模块-http://jsfiddle.net/hhsja/1/-850MB,并且还在增加
- 异步模块-http://jsfiddle.net/SgemT/-1.2GB并不断增加
服务器和客户端位于不同的计算机上。(Softlayer云实例)。节点0.10.12和Socket.io 0.9.16
为什么会发生这种情况?如何保持低内存并使用某种允许保持代码可读性的库?
选项1。您可以使用集群模块,不时优雅地杀死您的工作人员(确保先断开连接())。您可以在master中检查process.memoryUsage().rss>113000000,并在工人超过130MB时杀死他们,例如:)
选项2。NodeJS有使用内存的习惯,很少进行严格的清理。当V8达到最大内存限制时,GC调用会更加激进。因此,您可以通过运行node --max-stack-size <amount>
来降低节点进程可能占用的最大内存。我在嵌入式设备上运行node时会这样做(通常可用内存少于64MB)。
选项3。如果您真的想保持低内存,请尽可能使用弱引用(除了长时间运行的调用之外的任何地方)https://github.com/TooTallNate/node-weak。这样,对象将更快地被垃圾收集。不过,需要进行广泛的测试以确保一切正常。GL如果你使用这个:)https://github.com/TooTallNate/node-weak
问题似乎出在客户端脚本上,而不是服务器脚本上。我运行了1000个进程,每个进程每秒都会向服务器发送消息。我认为服务器正忙于解决所有这些请求,从而使用所有内存。我这样重写客户端,生成与处理器数量成比例的多个进程,每个进程连接多次,如下所示:
client = io.connect(selectedEnvironment, { 'force new connection': true, 'reconnect': false });
请注意"强制新连接"标志,它允许使用socket.io-client的同一实例连接多个客户端。解决我问题的部分实际上是如何发出请求的:任何客户端都会在收到前一个请求的确认后一秒钟发出另一个请求,而不是每一秒钟。连接1000个客户端使我的服务器使用大约100MB的RSS。我还在服务器上使用了async脚本,它看起来非常优雅,比Q更容易理解。糟糕的是,我已经运行服务器大约2-3天了,内存增加到250MBRSS。我不知道为什么。