在sidekiq中标记作业以便将来快速搜索和删除

时间:2017-03-02 12:56:48

标签: ruby-on-rails ruby-on-rails-4 redis sidekiq

我有一个用例,我想在将来发生某些事件时清除一些sidekiq作业。

一种方法是将job_ids存储在某处(比如redis),然后使用它来搜索和删除作业。

 Sidekiq::ScheduledSet.new.find_job([job_id]).delete

但是我必须将它存储在redis中,并在队列中的所有作业中进行线性搜索。

另一种方法是在worker中添加一个额外的参数。然后使用它进行搜索并删除。

Sidekiq::ScheduledSet.new.find {|j| j.queue == 'my_queue' && j.args[0] == "my_tag_user_id"}.map(&:delete)

这样,至少我不必担心在redis中存储工作ID。但是,我不会更快地进行搜索,看起来有点像一个hacky解决方案。

我需要建议什么是在sidekiq中为给定用户标记某些作业的最佳方法,然后在以后快速搜索它们以进行删除。

1 个答案:

答案 0 :(得分:0)

Sidekiq的内部数据结构未针对此类操作进行优化。而是为与用户关联的作业创建事务ID,并将其存储在数据库中。

tid = SecureRandom.hex(16)
user.update_column(:tid, tid)
10.times { SomeWorker.perform_async(user.id) }

当未来事件发生时,在Redis中设置一个标志,表示应取消与此事务ID关联的所有作业。

Sidekiq.redis {|c| c.setex(user.tid, 2.weeks, 1) }

当作业运行时,他们应该做的第一件事就是检查它们是否已被取消。如果是这样,他们只是立即返回而不做任何事情。

def perform(user_id)
  user = User.find(user_id)
  return if cancelled?(user.tid)
  do_stuff
end