Иногда Resque выгружает среду Rails без видимой причины

У меня есть простой стек с Ruby on Rails и resque. Я ставлю задания в очередь обычным образом, и у меня есть пул рабочих, которые работают. Ничего сумасшедшего.

Моя проблема в том, что если я оставлю воркеры работать достаточно долго, они перестанут видеть модели приложения, и каждый вызов такого метода приведет к ошибке undefined_method.

Это очень странно, так как он может отлично работать в течение нескольких дней, а потом вдруг начинает давать сбой. Перезапуск рабочего решает проблему, но обычно она возвращается через некоторое время.

Я понятия не имею, что может происходить, поэтому любые указатели будут очень признательны.


person marcgg    schedule 06.12.2011    source источник
comment
Вы делаете какие-то релизы в это время? Capistrano удаляет файлы, над которыми работает resque, или что-то в этом роде?   -  person phoet    schedule 06.12.2011
comment
@phoet Это происходит в разработке. У меня еще нет производственной среды. Я могу менять файлы, но это должно иметь значение, когда они загружаются рабочими - я думаю   -  person marcgg    schedule 07.12.2011
comment
Не могли бы вы опубликовать трассировку стека того, что происходит во время сбоя? Мне похоже, что ваши работники потеряли соединение с базой данных, а не с кодом приложения, уходящим в самоволку. Но я не пользователь Rails/Activerecord, поэтому я не уверен.   -  person Luke Antins    schedule 16.12.2011


Ответы (1)


Спасатели создают новые процессы для выполнения работы. Возможно, классы для ваших моделей не загружены в разветвленном дочернем процессе. Также возможен конфликт пространств имен из-за порядка загрузки классов.

Если вы меняете файлы классов в процессе разработки без перезапуска рабочих resque, я подозреваю, что они неправильно перезагружают ваши классы.

Чтобы убедиться, что ваши классы загружены до разветвления, сошлитесь на классы в задаче настройки resque. Классы, которые загружены до разветвления, будут скопированы в дочерний процесс. Ниже я помещаю их в массив, чтобы заставить их загружаться. Это также быстрее, поскольку в каждый дочерний процесс уже загружены классы. Также вам следует восстановить соединение ActiveRecord в блоке after_fork, если вы используете AR.

lib/tasks/resque.rake:

namespace :resque do
  task :setup => :environment do
    [User, Monkey, Banana] # force these classes to load

    Resque.after_fork { ActiveRecord::Base.establish_connection }
  end
end
person tee    schedule 19.12.2011
comment
Почему мы должны переустанавливать AR-соединение в after_fork? - person Apoorv Parijat; 29.09.2013