Node.js如何使用单线程处理并发请求?

9

我在这个问题上进行了一些搜索, 但似乎人们只重视非阻塞IO。

假设我只有一个非常简单的应用程序,向客户端响应“Hello World”文本,它仍然需要时间来完成执行,无论多快。如果恰好同时出现两个请求,Node.js如何确保两个请求将通过一个线程处理?

我阅读了博客《理解node.js事件循环》,其中提到“当然,在后端,有用于数据库访问和进程执行的线程和进程”。 这个声明是关于IO的,但我也想知道是否有单独的线程来处理请求队列。如果是这种情况,那么我可以说Node.js单线程概念只适用于在Node.js上构建应用程序的开发人员,但Node.js实际上在幕后运行在多线程上吗?


请注意,在node.js中,“除了您的代码,一切都是并行运行的”。您的代码在单个线程上运行,但事件在幕后由多个线程处理。 - user1481317
@BibekSubedi,我谷歌搜索了“在node.js中,除了你的代码,一切都是并行运行的”,它帮助澄清了一些困惑,谢谢。 - Dino Tw
1个回答

10
操作系统为每个套接字连接提供了一个发送和接收队列,这就是字节的位置,直到应用程序层处理它们。如果接收队列填满,没有连接的客户端就不能发送信息,直到队列中有可用空间。这就是为什么应用程序应该尽快处理请求的原因。
如果您使用的是*nix系统,则可以使用netstat查看发送和接收队列中的当前字节数。在此示例中,接收队列中没有字节,发送队列中有240个字节(等待操作系统发送)。
Proto Recv-Q Send-Q Local Address               Foreign Address             State
tcp        0      240 x.x.x.x:22                 x.x.x.x:*                   LISTEN

在Linux上,您可以使用proc文件系统检查发送/接收队列的默认大小和最大允许大小:

Receive:

cat /proc/sys/net/core/rmem_default
cat /proc/sys/net/core/rmem_max

Send:

cat /proc/sys/net/core/wmem_max
cat /proc/sys/net/core/wmem_default

那么你的意思是Node.js依赖于操作系统来排队请求,它没有自己的实现来处理队列,对吗? - Dino Tw
我还是有些困惑。我刚刚在Node的关于页面上读到了这与当今更常见的并发模型形成对比,后者使用操作系统线程。看起来Nodejs没有使用操作系统线程,但我不确定我是否理解正确。 - Dino Tw
他们正在讨论单线程与每个连接一个线程的问题。 - Michael
Node.js并没有做任何特别的事情,你可以在大多数语言中使用非阻塞IO并在应用程序中使用单个线程。Java支持它,并且Netty库使其在Java中易于实现。通常,您使用单个线程处理所有内容,如果某些操作需要“长时间”(长时间的定义取决于您的应用程序以及请求的速度),则会生成一个线程来处理长时间运行的操作(例如需要Web服务调用的请求)。 - Michael
1
如果你担心同时发生多个请求,那么你就要降到网络层。让操作系统来处理这个问题。 - Michael
显示剩余3条评论

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接