我正在一个小团队中开发单页应用程序,该应用程序严重依赖WebSockets上的低延迟查询。后端在Node.js + Redis上运行。它需要支持数百至数千个同时连接,并且请求必须在50-100毫秒(在客户端的良好网络条件下)下得到服务。我们对该服务器的这一部分的初始实现感到非常满意,它的性能符合预期。
我们还需要通过HTTP提供大量静态文件。这些请求不是时间敏感的。由于存储需求巨大,出于成本原因,我们希望选择使用一系列HDD代替SSD。
是否存在磁盘I / O速度慢的风险,从而降低其余Node.js应用程序的性能(WebSocket部分仅使用内存数据库)还是会严格影响HTTP /静态文件服务部分服务器?据我所知,具有异步特性的Node.js非常适合这种情况,因为它允许WebSockets模块在HTTP模块等待磁盘读/写时正常处理查询?
也许大量的“等待服务” HTTP请求可能以某种方式阻塞服务器(毕竟,它们需要存储在某个地方,并且如果可以进行读/写操作,则可能无法自由轮询)并且我们需要考虑使用单独的Node.js进程来提供静态文件,甚至完全使用单独的专用服务器?
我可以想到以下几点:
我们还不能在现实世界中测试这种情况,因此,我很感谢收到具有类似经验的任何人的来信。这可能需要我们重新考虑架构,这是我们最好早发现的事情。
答案 0 :(得分:1)
如果来自客户端的请求很多,则需要通过Cluster API https://nodejs.org/api/cluster.html使用负载均衡器 您还需要考虑使用缓存,因为HTTP和光盘操作确实很昂贵。如果这些还不够,您只需添加新服务器即可。这就是我的工作方式,并且了解解决高负载问题的方法。
P。 S.我不认为node.js是个问题,它是诸如提供静态文件之类的东西的好平台。您只是有很多请求,您需要使用我描述的方法来解决此问题。
答案 1 :(得分:1)
简短答案:是:存在巨大风险:p
https://nodejs.org/api/fs.html#fs_threadpool_usage
线程池用法#
除fs.FSWatcher()之外的所有文件系统API 显式同步使用libuv的线程池,该线程池可以具有 对某些人而言具有令人惊讶和负面的性能影响 应用程序。有关更多信息,请参见UV_THREADPOOL_SIZE文档。 信息。
http://docs.libuv.org/en/v1.x/design.html#file-i-o
UV Threadpool由系统线程支持,因此缩放配置文件将与应用程序的其余部分完全不同。 IMO这并不一定要冒更大的风险……不同而困难的数据将有助于查看您应用程序的缩放比例。
我认为的一般最佳做法是,尽可能卸载静态文件的服务。在您的应用程序前面安装一个能够快速提供静态文件(nginx)的代理可能会有所帮助(不是因为它解决了阻止文件系统读取的核心问题,而是因为它 可以提供更统一/可预测的性能或扩展性,因为它只需要管理提供的文件,而您的应用程序则需要在用户和提供的文件之间进行上下文切换。我个人将研究您建议使用单独的进程或CDN尝试从中完全删除静态文件的提供您的应用程序。