Rails Thread.current 变量是否与单个用户请求隔离?

Are Rails Thread.current variables isolated to a single user request?

我正在使用 Thread.current 来存储当前用户 ID,以便我可以看到谁对我们的数据库进行了各种更新。但是,在生产中使用了一些之后,它会返回其他用户 ID,而不是那些可以更新此数据的用户 ID。在本地和较少使用的 QA 实例上,保存的用户 ID 是合适的。

我们在 Puma 中使用 Rails 5.1、ruby 2.5.1。 RAILS_MAX_THREADS=1,但我们确实有 RAILS_POOL_SIZE=5。任何可能导致此问题或如何解决的想法?具体来说,单个 Thread.current 变量的持续时间是否比单个用户请求的持续时间长?

为什么 Thread.current 仅限于一个请求?

同一个线程用于多个请求。

线程不会在请求结束时被杀死,它们只是从队列中获取下一个请求(或等待请求到达队列)。

如果您使用 Timeout 中间件,情况会有所不同,因为超时实际上使用线程来计算时间的流逝(并停止处理)...但是为每个请求创建新线程会引入性能成本。

旁注

根据您的数据库使用情况(阻塞 IO),RAILS_MAX_THREADS 可能需要更高。您拥有的数据库调用/数据越多,线程阻塞数据库 IO 的时间就越多(本质上是睡眠)。

通过将线程池限制为单个线程,您在很大程度上限制了请求并发。 CPU 可能正在处理其他请求,同时等待数据库 return 数据。