Ruby-on-rails 在 Delayed_job 中手动重试作业

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/3312054/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-02 22:56:44  来源:igfitidea点击:

Manually Retry Job in Delayed_job

ruby-on-railsrubyrubygemsdelayed-job

提问by Michael Waxman

Delayed::Job's auto-retry feature is great, but there's a job that I want to manually retry now. Is there a method I can call on the job itself like...

Delayed::Job 的自动重试功能很棒,但是我现在想手动重试一个作业。有没有一种方法可以在工作本身上调用,例如...

Delayed::Job.all[0].perform

or run, or something. I tried a few things, and combed the documentation, but couldn't figure out how to execute a manual retry of a job.

或运行,或什么。我尝试了一些东西,并梳理了文档,但无法弄清楚如何执行作业的手动重试。

回答by The Who

To manually call a job

手动调用作业

Delayed::Job.find(10).invoke_job # 10 is the job.id

This does not remove the job if it is run successfully. You need to remove it manually:

如果作业成功运行,这不会删除作业。您需要手动删除它:

Delayed::Job.find(10).destroy

回答by Beena Shetty

Delayed::Worker.new.run(Delayed::Job.last)

This will remove the job after it is done.

这将在完成后删除作业。

回答by Joe Martinez

You can do it exactly the way you said, by finding the job and running perform.

你可以完全按照你说的那样做,通过找到工作并运行执行。

However, what I generally do is just set the run_at back so the job processor picks it up again.

但是,我通常所做的只是将 run_at 设置回原处,以便作业处理器再次拾取它。

回答by Tony

I have a method in a controller for testing purposes that just resets all delayed jobs when I hit a URL. Not super elegant but works great for me:

我在控制器中有一个用于测试目的的方法,它在我点击 URL 时重置所有延迟的作业。不是超级优雅,但对我很有用:

# For testing purposes
  def reset_all_jobs
    Delayed::Job.all.each do |dj|
      dj.run_at = Time.now - 1.day
      dj.locked_at = nil
      dj.locked_by = nil
      dj.attempts = 0
      dj.last_error = nil
      dj.save
    end
    head :ok
  end

回答by jpw

Prior answers above might be out of date. I found I needed to set failed_at, locked_by, and locked_at to nil:

以上先前的答案可能已过时。我发现我需要将 failed_at、locked_by 和 locked_at 设置为 nil:

(for each job you want to retry):

(对于您要重试的每个作业):

d.last_error = nil
d.run_at = Time.now
d.failed_at = nil
d.locked_at = nil
d.locked_by = nil
d.attempts = 0
d.failed_at = nil # needed in Rails 5 / delayed_job (4.1.2)
d.save!

回答by mohamed-ibrahim

if you have failed delayed job which you need to re-run, then you will need to only select them and set everything refer to failed retry to null:

如果您的延迟作业失败并需要重新运行,那么您只需要选择它们并将所有引用失败重试的内容设置为空:

Delayed::Job.where("last_error is not null").each do |dj|
  dj.run_at = Time.now.advance(seconds: 5)
  dj.locked_at = nil
  dj.locked_by = nil
  dj.attempts = 0
  dj.last_error = nil
  dj.failed_at = nil
  dj.save  
end

回答by Darme

In a development environment, through rails console, following Joe Martinez's suggestion, a good way to retry all your delayed jobs is:

在开发环境中,rails console按照 Joe Martinez 的建议,通过,重试所有延迟作业的好方法是:

Delayed::Job.all.each{|d| d.run_at = Time.now; d.save!}

回答by rubycop

Delayed::Job.all.each(&:invoke_job)

回答by Blair Anderson

Put this in an initializer file!

把它放在一个初始化文件中!

module Delayed
  module Backend
    module ActiveRecord
      class Job
        def retry!
          self.run_at = Time.now - 1.day
          self.locked_at = nil
          self.locked_by = nil
          self.attempts = 0
          self.last_error = nil
          self.failed_at = nil
          self.save!
        end
      end
    end
  end
end

Then you can run Delayed::Job.find(1234).retry!

然后你可以运行 Delayed::Job.find(1234).retry!

This will basically stick the job back into the queue and process it normally.

这基本上会将作业重新放入队列并正常处理。