1

我知道 Python 的 GIL 并且 Python 中的线程并不像在 Go 中生成一个 go 例程那么容易。然而,在我看来,Ruby 能够与 Puma 和 Unicorn 一起实现多线程并发。我的问题实际上是双重的。我的经验仅限于 Django Channel 的 Daphne。

  1. 除了 Daphne,Rails 中的 puma 和 unicorn 等多线程的 Web 服务器还有哪些选择?

  2. 从 Daphne 的文档中,我了解到并行性是通过产生新进程(工人)来实现的

    因为运行消费者的工作与与 HTTP、WebSocket 和其他客户端连接的通信工作是解耦的,所以您需要运行一个“工作服务器”集群来完成所有处理。每台服务器都是单线程的,因此建议您在每台机器上的每个内核上运行一个或两个左右;在同一台机器上运行尽可能多的并发工作人员是安全的,因为他们不打开任何端口(他们所做的只是与通道后端交谈)。

如前所述,每个工作人员都是单线程的。当涉及到 I/O 函数调用时,worker 完全被阻塞了。我的问题是,为什么 Daphne 不能为每个请求生成多个线程。当一个线程被 I/O 阻塞时,例如数据库访问,CPU 切换到执行另一个线程,直到前一个线程被解除阻塞。同样,Node.js 是单线程的,但它通过非阻塞 I/O 很好地实现了并发性。为什么很难实现同样的壮举。在 Python 中?(除了它缺乏良好的事件循环之外。)

4

2 回答 2

2

目前,uvicorn是 daphne 的唯一替代品,它支持多处理并准备好用于生产用途。

$ pip install uvicorn

$ uvicorn avilpage.asgi --workers 4

这将启动有 4 个工作人员的服务器。

由于 daphne/uvicorn 使用 asyncio 进行多任务,我猜多线程没有意义。

于 2018-06-08T05:49:56.020 回答
0

工人不是单线程的。它们中的每一个都打开一个线程池来运行所有数据库查询以及您运行 sync_to_async 的任何内容。Daphne 的重点是异步,你在主线程中使用 asyncio 保留的越多,它运行的速度就越快。您希望尽可能地消除上下文切换,以便 CPU 缓存保持新鲜。此外,Python 的 GIL 一次只保持一个线程工作,这就是为什么多线程不会提高速度的原因。你可以有 25 个线程,它的运行速度和 1 个线程一样快:https ://gist.github.com/agronick/692d9a7bc41b75449f8f5f7cad93a924

于 2018-07-06T20:59:17.213 回答