活动记录mySQL超时错误--:worker=0 PID:(xxxxx)超时(61s>;60s),终止

活动记录mySQL超时错误--:worker=0 PID:(xxxxx)超时(61s>;60s),终止,mysql,ruby-on-rails,ruby,activerecord,timeout,Mysql,Ruby On Rails,Ruby,Activerecord,Timeout,我的控制器上有一个异步操作,可以根据用户输入执行大量SQL查询 @results = ActiveRecord::Base .connection .select_all(query_string) .map do |record| Hashie::Mash.new(record) end 发生这种情况时,我从服务器得到的唯一响应是 E, [2020-02-05T16:14:04.133233 #59909] ERROR -- : worker=0 PID:6095

我的控制器上有一个异步操作,可以根据用户输入执行大量SQL查询

  @results = ActiveRecord::Base
  .connection
  .select_all(query_string)
  .map do |record|
    Hashie::Mash.new(record)
  end
发生这种情况时,我从服务器得到的唯一响应是

E, [2020-02-05T16:14:04.133233 #59909] ERROR -- : worker=0 PID:60952 timeout (61s > 60s), killing
E, [2020-02-05T16:14:04.159372 #59909] ERROR -- : reaped #<Process::Status: pid 60952 SIGKILL (signal 9)> worker=0
E[2020-02-05T16:14:04.133233 59909]错误--:worker=0 PID:60952超时(61s>60s),终止
E、 [2020-02-05T16:14:04.159372#59909]错误--:收割的工人=0
是否有任何方法可以在后端捕获此超时,以向用户提供正确的反馈


尝试使用
超时::超时(x)
,但没有成功。

您可以自己添加另一个较短的超时,并在工作人员死亡之前处理该情况。像这样的事情可能是一个好的开始:

require 'timeout'

begin
  # 5 seconds before the MySQL timeout would kick in
  Timeout.timeout(55) do
    # have only the slow query in this block
    @database_results = ActiveRecord::Base.connection.select_all(query_string)
  end
rescue Timeout::Error
  # Handle the timeout. Proper error handling depends on your application.
  # In a controller you might just want to return an error page, in a 
  # background worker you might want to record the error in your database.
end

# time to translate the data should not count towards the timeout
@results = @database_results.map  { |r| Hashie::Mash.new(r) }

你可以用一个稍微短一点的超时来扭曲它,而不是在发生这种情况时处理工作中的情况。但这真的是正确的方法吗?我会专注于加快查询速度,或者让查询运行时间超过60秒。但是在代码中有一个查询由于超时原因而随机失败,这让我觉得很奇怪。我同意@spickermann的观点,不幸的是,现在重新设计整个功能是不可能的,但正确的方法是在你的应用程序中绝对没有这些功能。我尝试了一个小超时,但结果是:ActiveRecord::StatementInvalid(Mysql2::Error:此连接仍在等待结果,请在获得结果后重试: