Resque作业,如何停止正在运行的作业

Posted

技术标签:

【中文标题】Resque作业,如何停止正在运行的作业【英文标题】:Resque jobs, how to stop running job 【发布时间】:2013-12-04 13:00:05 【问题描述】:

我的 Resque 工人阶级

class WebWorker

  @queue = :jobs_queue

  def self.perform(id)
  //bunch of code here
  end
end

我从队列中删除了一个这样的工作

Resque.dequeue(WebWorker,id)

但我想停止运行作业并重新启动,我该怎么做?

【问题讨论】:

***.com/questions/7416318/… 【参考方案1】:

试试unregister_worker如下:

Resque.workers.each(&:unregister_worker)

此命令将停止工作并将其设置为失败。

http://www.rubydoc.info/gems/resque/Resque/Worker:unregister_worker

【讨论】:

这不仅会停止正在运行的作业,还会永久停止整个工作器,没有好的方法可以恢复它(只有重新启动服务器才能恢复)。【参考方案2】:

如果您想杀死/停止正在进行的作业而不将其标记为失败的作业,您可以使用此 hack。

class Task

    @queue = :queue_name

    def self.perform(parameters)

        pid = Process.fork do
            Task.work parameters
        end

        #puts "parent, pid #Process.pid, waiting on child pid #pid"
        Process.wait
    end

    def self.work(parameters)
        #Your perform code here
    end
end

现在,您想在哪里停止此代码,只需联系当前正在执行您想停止的工作的 resque 工作人员。并杀死其孩子的子进程。类似于杀死 Worker 的孙子进程。

说明:

worker 派生出一个子进程,其中 perform 函数运行其代码。如果我们直接杀死这个子进程,那么这个作业将停止,但它会被标记为失败的作业。这就是为什么我们在 self.perform 中派生了另一个子进程,现在杀死 perform 的子进程将停止这个正在运行的作业,并且它不会被标记为失败。现在我们可以再次将作业排入队列。因此,任务是如何联系正在执行我们需要停止的工作的工人 (._.")

我已经通过为基于 UNIX 的系统编写这段代码来做到这一点:

Resque.workers.each do |worker|
    #If condition : "current worker is working and is working on the job that we want to stop and is operating on the queue that we require " and please change this condition as per your requirement          
    if worker.working? and worker.queues.include?("queue_name") and worker.job["payload"]["args"].first==post_id
            victim = %x[pgrep -P #worker.pid] #Getting child's PID
            victim.strip!
            victim = %x[pgrep -P #victim] #Getting grandchild's PID of worker
            victim.strip!
            %x[kill -9 #victim.to_i]
    end
end

【讨论】:

以上是关于Resque作业,如何停止正在运行的作业的主要内容,如果未能解决你的问题,请参考以下文章

如何破坏由resque工人排队的工作?

Rails.root 在 Resque 作业期间指向生产中的错误目录

如何在不清除整个队列的情况下从 Resque 队列中删除特定作业?

如何停止长时间运行的 BigQuery 作业?

Sidekiq 停止一项正在运行的作业

如何杀死正在运行的 google AUTOML 训练作业