class SidekiqUniqueJobs::Lock::BaseLock
@author Mikael Henriksson <mikael@mhenrixon.com>
@abstract
Abstract base class for locks
def self.validate_options(options = {})
-
(void)
-
Parameters:
-
options
(Hash
) -- the sidekiq_options given to the worker
def self.validate_options(options = {}) Validator.validate(options) end
def call_strategy(origin:)
- Yieldreturn: - the yield is irrelevant, it only provides a mechanism in
Other tags:
- Yieldparam: if - a new job id was set and a block is given
Returns:
-
(void)
- the return value is irrelevant
Parameters:
-
origin
(Symbol
) -- the origin `:client` or `:server`
def call_strategy(origin:) new_job_id = nil strategy = strategy_for(origin) @attempt += 1 strategy.call { new_job_id = lock if strategy.replace? && @attempt < 2 } yield if new_job_id && block_given? end
def callback_safely
def callback_safely callback&.call item[JID] rescue StandardError reflect(:after_unlock_callback_failed, item) raise end
def client_strategy
def client_strategy @client_strategy ||= OnConflict.find_strategy(lock_config.on_client_conflict).new(item, redis_pool) end
def execute
-
(NotImplementedError)
- needs to be implemented in child class
def execute raise NotImplementedError, "##{__method__} needs to be implemented in #{self.class}" end
def initialize(item, callback, redis_pool = nil)
-
redis_pool
(Sidekiq::RedisConnection, ConnectionPool
) -- the redis connection -
callback
(Proc
) -- the callback to use after unlock -
item
(Hash
) -- the Sidekiq job hash
def initialize(item, callback, redis_pool = nil) @item = item @callback = callback @redis_pool = redis_pool @attempt = 0 prepare_item # Used to ease testing @lock_config = LockConfig.new(item) end
def lock
- Yield: - to the caller when given a block
Returns:
-
(String, nil)
- the locked jid when properly locked, else nil.
Other tags:
- Note: - Will call a conflict strategy if lock can't be achieved.
def lock raise NotImplementedError, "##{__method__} needs to be implemented in #{self.class}" end
def locksmith
-
(SidekiqUniqueJobs::Locksmith)
- the locksmith for this sidekiq job
Other tags:
- Api: - private
def locksmith @locksmith ||= SidekiqUniqueJobs::Locksmith.new(item, redis_pool) end
def prepare_item
-
(void)
- the return value should be irrelevant
def prepare_item return if item.key?(LOCK_DIGEST) # The below should only be done to ease testing # in production this will be done by the middleware SidekiqUniqueJobs::Job.prepare(item) end
def server_strategy
def server_strategy @server_strategy ||= OnConflict.find_strategy(lock_config.on_server_conflict).new(item, redis_pool) end
def strategy_for(origin)
def strategy_for(origin) case origin when :client client_strategy when :server server_strategy else raise SidekiqUniqueJobs::InvalidArgument, "#origin needs to be either `:server` or `:client`" end end
def unlock_and_callback
def unlock_and_callback return callback_safely if locksmith.unlock reflect(:unlock_failed, item) end