我使用firebird数据库gem连接到用户指定的数据库。只要用户提供正确的数据,它就可以正常工作。如果没有,gem无法连接,并且gem抛出异常需要很长时间。我尝试过使用超时:超时如下:
database = Fb:Database(connection_data)
Timeout::timeout(5) do
database.connect #that's the part that takes long to connect
end
但它没有超时。它只是等待(这是一个漫长的等待,超过一分钟),并抛出宝石异常(它不是超时异常)。似乎代码执行时间低于5秒(根据Timeout),除了花了1-2分钟。我一直在寻找解释(检查源代码),但没有找到任何解释。我真的不想修复它(因为它会被转移到延迟的工作),但我想知道为什么,你怎么能忽略Timeout。
此外,下面的代码工作正常。
Timeout::timeout(5) do
sleep(10)
end
答案 0 :(得分:1)
超时块在新线程中运行代码,当timeout
在5秒后发生时,异常被强制引发(Thread.raise
我相信)进入运行database.connect
的线程。 (Timeout module code)
这种中断可能发生在任何一条线上;在这种情况下,它可能在某种救援块中(并在之后抛出自定义错误)或任何无法正确处理它的地方,使其处于无效状态。图书馆不太可能在任何地方进行防御性编码。
您可以详细了解在this Reddit thread中使用Timeout::timeout
的问题。