11

我有一个接受图像上传的应用程序。这是 Heroku 上使用 Unicorn 的 rails 3 应用程序。我偶尔会遇到unicorn::clientshutdown异常,我真的不知道是什么原因导致它们或如何处理它们。我应该怎么办?

这是我的unicorn.rb文件:

before_fork do |server, worker|
  # Replace with MongoDB or whatever
  if defined?(ActiveRecord::Base)
    ActiveRecord::Base.connection.disconnect!
    Rails.logger.info('Disconnected from ActiveRecord')
  end

  # If you are using Redis but not Resque, change this
  if defined?(Resque)
    Resque.redis.quit
    Rails.logger.info('Disconnected from Redis')
  end
end

after_fork do |server, worker|
  # Replace with MongoDB or whatever
  if defined?(ActiveRecord::Base)
    ActiveRecord::Base.establish_connection
    Rails.logger.info('Connected to ActiveRecord')
  end

  # If you are using Redis but not Resque, change this
  if defined?(Resque)
    Resque.redis = ENV['REDIS_URI']
    Rails.logger.info('Connected to Redis')
  end
end
4

1 回答 1

4

图片上传、Heroku 和 Unicorn,哦,我的。

问题

这是此错误的三连胜。Heroku 日志中可能存在相关的 H12 错误 ( https://devcenter.heroku.com/articles/error-codes#h12-request-timeout )。发生的情况是请求完成的时间太长(Heroku 有一个不可避免的 30 秒超时),所以它断开连接并且那个独角兽工人被杀死了。此外,Unicorn 不适合处理缓慢/长时间运行的请求(请参阅http://rainbows.rubyforge.org

解决方案

诀窍是在前端上传图像而不访问服务器(CORS/AJAX/jquery.fileupload.js/etc),将上传的文件位置与表单提交一起传递,然后作为后台作业执行任何处理并重新上传,不受 30 秒超时限制。其他人对此进行了更广泛的报道。此外,您可以使用 Cloudinary 之类的服务为您执行此操作。

附言

YMMV,但您也应该将其添加到您的独角兽配置中(https://devcenter.heroku.com/articles/rails-unicorn

before_fork do |server, worker|
  Signal.trap 'TERM' do
    puts 'Unicorn master intercepting TERM and sending myself QUIT instead'
    Process.kill 'QUIT', Process.pid
  end
  # ...
end

after_fork do |server, worker|
  Signal.trap 'TERM' do
    puts 'Unicorn worker intercepting TERM and doing nothing. Wait for master to sent QUIT'
  end
  # ...
end
于 2014-04-01T23:05:50.107 回答