2013-11-20 31 views
8

我Resque工人阶级Resque工作,如何停止正在运行的任务

class WebWorker 

    @queue = :jobs_queue 

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

我从队列中删除某项工作这样

Resque.dequeue(WebWorker,id) 

但我想停止正在运行的任务并重新启动,我该怎么做?

+1

http://stackoverflow.com/questions/7416318/how-do-i-clear-stuck-stale-resque-workers – snowangel

回答

1

如果你觉得杀/停止正在进行的工作,而不将其标记为失败的作业,你可以使用这个技巧。

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工人目前正在做要停止作业。并杀死孩子的孩子进程。像杀害工人的孙子过程。

说明:

一名工人叉子进程中执行函数来运行其代码。如果我们直接杀死这个子进程,那么这个工作将停止,但它会被标记为失败的工作。这就是为什么我们在self.perform中派生了另一个子进程,并且现在kill执行的子进程将会停止这个正在运行的作业,并且它也不会被标记为失败。现在我们可以再次入选这份工作。所以,任务是如何达到的工人这样做,我们需要停止工作

我已成功地做到这一点通过编写一个基于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 
相关问题