2016-11-22 49 views
0

sidekiq中的作业是假设检查它们是否被取消,但是如果我有一个长时间运行的作业,我希望它定期检查自己。这个例子不起作用:我没有将假工作包装在任何未来,我可以提出异常 - 我不知道甚至有可能。我该怎么做?定期检查一个sidekiq作业是否已被取消

class ThingWorker 

    def perform(phase, id) 
    thing = Thing.find(id) 

    # schedule the initial check 
    schedule_cancellation_check(thing.updated_at, id) 

    # maybe wrap this in something I can raise an exception within? 
    sleep 10 # fake work 
    @done = true 

    return true 
    end 


    def schedule_cancellation_check(initial_time, thing_id) 
    Concurrent.schedule(5) { 

     # just check right away... 
     return if @done 

     # if our thing has been updated since we started this job, kill this job! 
     if Thing.find(thing_id).updated_at != initial_time 
     cancel! 

     # otherwise, schedule the next check 
     else 
     schedule_cancellation_check(initial_time, thing_id) 
     end 
    } 
    end 

    # as per sidekiq wiki 
    def cancelled? 
    @cancelled 
    Sidekiq.redis {|c| c.exists("cancelled-#{jid}") } 
    end 

    def cancel! 
    @cancelled = true 
    # not sure what this does besides marking the job as cancelled tho, read source 
    Sidekiq.redis {|c| c.setex("cancelled-#{jid}", 86400, 1) } 
    end 

end 

回答

0

你在想这种方式太难了。您的工作人员应该是一个循环,并在每次迭代时检查取消。

def perform(thing_id, updated_at) 
    thing = Thing.find(thing_id) 
    while !cancel?(thing, updated_at) 
    # do something 
    end 
end 

def cancel?(thing, last_updated_at) 
    thing.reload.updated_at > last_updated_at 
end