我正在尝试在应用程序中使用 EM-Synchrony 进行并发,但在使用延迟代码和 Fibers 时遇到了问题。
在 EM.defer 或 EM::Synchrony.defer 中对数据库的任何调用都会导致应用程序因错误而崩溃can't yield from root fiber
下面是我正在尝试完成的一个非常精简的可运行示例。第一个打印工作并显示[:first, 1]
,但第二个是我因上述错误而崩溃的地方。
require 'mysql2'
require 'em-synchrony/activerecord'
ActiveRecord::Base.establish_connection(
:adapter => 'em_mysql2',
:username => 'user',
:password => 'pass',
:host => 'localhost',
:database => 'app_dev',
:pool => 60
)
class User < ActiveRecord::Base; end
EM.synchrony do
p [:first, User.all.count]
EM::Synchrony.defer do
p [:second, User.all.count]
end
end
我的第一个想法可能是 EM::Synchrony.defer 中的 Fiber.current 和 Fiber.yield 意味着我可以通过额外的 Fiber.new 调用来解决问题
EM::Synchrony.defer do
Fiber.new do
p [:second, User.all.count]
end.resume
end
这也无法运行,但这次我得到了错误fiber called across threads
。