redis_queued_locks 1.12.1 → 1.14.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
 - data/.rubocop.yml +3 -1
 - data/.ruby-version +1 -1
 - data/CHANGELOG.md +45 -5
 - data/LICENSE.txt +1 -1
 - data/README.md +574 -296
 - data/Rakefile +12 -4
 - data/Steepfile +15 -0
 - data/github_ci/ruby3.3.gemfile +17 -0
 - data/github_ci/ruby3.3.gemfile.lock +217 -0
 - data/lib/redis_queued_locks/{acquier → acquirer}/acquire_lock/delay_execution.rb +4 -4
 - data/lib/redis_queued_locks/acquirer/acquire_lock/dequeue_from_lock_queue/log_visitor.rb +40 -0
 - data/lib/redis_queued_locks/{acquier → acquirer}/acquire_lock/dequeue_from_lock_queue.rb +17 -8
 - data/lib/redis_queued_locks/acquirer/acquire_lock/instr_visitor.rb +166 -0
 - data/lib/redis_queued_locks/acquirer/acquire_lock/log_visitor.rb +218 -0
 - data/lib/redis_queued_locks/acquirer/acquire_lock/try_to_lock/log_visitor.rb +543 -0
 - data/lib/redis_queued_locks/{acquier → acquirer}/acquire_lock/try_to_lock.rb +126 -92
 - data/lib/redis_queued_locks/{acquier → acquirer}/acquire_lock/with_acq_timeout.rb +14 -9
 - data/lib/redis_queued_locks/acquirer/acquire_lock/yield_expire/log_visitor.rb +76 -0
 - data/lib/redis_queued_locks/{acquier → acquirer}/acquire_lock/yield_expire.rb +42 -19
 - data/lib/redis_queued_locks/{acquier → acquirer}/acquire_lock.rb +74 -47
 - data/lib/redis_queued_locks/{acquier → acquirer}/clear_dead_requests.rb +5 -3
 - data/lib/redis_queued_locks/{acquier → acquirer}/extend_lock_ttl.rb +4 -3
 - data/lib/redis_queued_locks/{acquier → acquirer}/is_locked.rb +1 -1
 - data/lib/redis_queued_locks/{acquier → acquirer}/is_queued.rb +1 -1
 - data/lib/redis_queued_locks/{acquier → acquirer}/keys.rb +5 -5
 - data/lib/redis_queued_locks/{acquier → acquirer}/lock_info.rb +9 -5
 - data/lib/redis_queued_locks/{acquier → acquirer}/locks.rb +16 -3
 - data/lib/redis_queued_locks/{acquier → acquirer}/queue_info.rb +8 -6
 - data/lib/redis_queued_locks/{acquier → acquirer}/queues.rb +9 -2
 - data/lib/redis_queued_locks/{acquier → acquirer}/release_all_locks.rb +26 -21
 - data/lib/redis_queued_locks/{acquier → acquirer}/release_lock.rb +28 -22
 - data/lib/redis_queued_locks/acquirer/release_locks_of.rb +211 -0
 - data/lib/redis_queued_locks/acquirer.rb +19 -0
 - data/lib/redis_queued_locks/client.rb +317 -254
 - data/lib/redis_queued_locks/config/dsl.rb +94 -0
 - data/lib/redis_queued_locks/config.rb +236 -0
 - data/lib/redis_queued_locks/data.rb +2 -0
 - data/lib/redis_queued_locks/errors.rb +27 -11
 - data/lib/redis_queued_locks/instrument.rb +11 -4
 - data/lib/redis_queued_locks/logging/void_logger.rb +38 -1
 - data/lib/redis_queued_locks/logging.rb +20 -5
 - data/lib/redis_queued_locks/resource.rb +49 -11
 - data/lib/redis_queued_locks/swarm/acquirers.rb +17 -16
 - data/lib/redis_queued_locks/swarm/flush_zombies.rb +26 -25
 - data/lib/redis_queued_locks/swarm/probe_hosts.rb +20 -19
 - data/lib/redis_queued_locks/swarm/redis_client_builder.rb +3 -3
 - data/lib/redis_queued_locks/swarm/supervisor.rb +19 -6
 - data/lib/redis_queued_locks/swarm/swarm_element/isolated.rb +20 -18
 - data/lib/redis_queued_locks/swarm/swarm_element/threaded.rb +35 -27
 - data/lib/redis_queued_locks/swarm/zombie_info.rb +9 -9
 - data/lib/redis_queued_locks/swarm.rb +20 -41
 - data/lib/redis_queued_locks/utilities.rb +11 -2
 - data/lib/redis_queued_locks/version.rb +2 -2
 - data/lib/redis_queued_locks.rb +2 -3
 - data/rbs_collection.lock.yaml +28 -0
 - data/rbs_collection.yaml +17 -0
 - data/redis_queued_locks.gemspec +22 -23
 - data/sig/manifest.yml +6 -0
 - data/sig/redis_queued_locks/acquier.rbs +4 -0
 - data/sig/redis_queued_locks/acquirer/acquire_lock/delay_execution.rbs +9 -0
 - data/sig/redis_queued_locks/acquirer/acquire_lock/dequeue_from_lock_queue/log_visitor.rbs +21 -0
 - data/sig/redis_queued_locks/acquirer/acquire_lock/dequeue_from_lock_queue.rbs +26 -0
 - data/sig/redis_queued_locks/acquirer/acquire_lock/instr_visitor.rbs +71 -0
 - data/sig/redis_queued_locks/acquirer/acquire_lock/log_visitor.rbs +72 -0
 - data/sig/redis_queued_locks/acquirer/acquire_lock/try_to_lock/log_visitor.rbs +179 -0
 - data/sig/redis_queued_locks/acquirer/acquire_lock/try_to_lock.rbs +48 -0
 - data/sig/redis_queued_locks/acquirer/acquire_lock/with_acq_timeout.rbs +19 -0
 - data/sig/redis_queued_locks/acquirer/acquire_lock/yield_expire.rbs +41 -0
 - data/sig/redis_queued_locks/acquirer/acquire_lock/yield_with_expire/log_visitor.rbs +32 -0
 - data/sig/redis_queued_locks/acquirer/acquire_lock.rbs +52 -0
 - data/sig/redis_queued_locks/acquirer/clear_dead_requests.rbs +28 -0
 - data/sig/redis_queued_locks/acquirer/extend_lock_ttl.rbs +28 -0
 - data/sig/redis_queued_locks/acquirer/is_locked.rbs +9 -0
 - data/sig/redis_queued_locks/acquirer/is_queued.rbs +9 -0
 - data/sig/redis_queued_locks/acquirer/keys.rbs +10 -0
 - data/sig/redis_queued_locks/acquirer/lock_info.rbs +10 -0
 - data/sig/redis_queued_locks/acquirer/locks.rbs +16 -0
 - data/sig/redis_queued_locks/acquirer/queue_info.rbs +13 -0
 - data/sig/redis_queued_locks/acquirer/queues.rbs +16 -0
 - data/sig/redis_queued_locks/acquirer/release_all_locks.rbs +30 -0
 - data/sig/redis_queued_locks/acquirer/release_lock.rbs +38 -0
 - data/sig/redis_queued_locks/acquirer/release_locks_of.rbs +46 -0
 - data/sig/redis_queued_locks/client.rbs +235 -0
 - data/sig/redis_queued_locks/config/dsl.rbs +26 -0
 - data/sig/redis_queued_locks/config.rbs +23 -0
 - data/sig/redis_queued_locks/data.rbs +4 -0
 - data/sig/redis_queued_locks/debugger/interface.rbs +9 -0
 - data/sig/redis_queued_locks/debugger.rbs +13 -0
 - data/sig/redis_queued_locks/errors.rbs +43 -0
 - data/sig/redis_queued_locks/instrument/active_support.rbs +7 -0
 - data/sig/redis_queued_locks/instrument/sampler.rbs +9 -0
 - data/sig/redis_queued_locks/instrument/void_notifier.rbs +7 -0
 - data/sig/redis_queued_locks/instrument.rbs +15 -0
 - data/sig/redis_queued_locks/logging/sampler.rbs +9 -0
 - data/sig/redis_queued_locks/logging/void_logger.rbs +15 -0
 - data/sig/redis_queued_locks/logging.rbs +15 -0
 - data/sig/redis_queued_locks/resource.rbs +42 -0
 - data/sig/redis_queued_locks/swarm/acquirers.rbs +10 -0
 - data/sig/redis_queued_locks/swarm/flush_zombies.rbs +13 -0
 - data/sig/redis_queued_locks/swarm/probe_hosts.rbs +13 -0
 - data/sig/redis_queued_locks/swarm/redis_client_builder.rbs +19 -0
 - data/sig/redis_queued_locks/swarm/supervisor.rbs +26 -0
 - data/sig/redis_queued_locks/swarm/swarm_element/isolated.rbs +52 -0
 - data/sig/redis_queued_locks/swarm/swarm_element/threaded.rbs +61 -0
 - data/sig/redis_queued_locks/swarm/swarm_element.rbs +8 -0
 - data/sig/redis_queued_locks/swarm/zombie_info.rbs +24 -0
 - data/sig/redis_queued_locks/swarm.rbs +41 -0
 - data/sig/redis_queued_locks/utilities/lock.rbs +10 -0
 - data/sig/redis_queued_locks/utilities.rbs +12 -0
 - data/sig/redis_queued_locks/version.rbs +3 -0
 - data/sig/redis_queued_locks.rbs +14 -0
 - data/sig/vendor/active_support.rbs +9 -0
 - data/sig/vendor/redis_client.rbs +39 -0
 - data/sig/vendor/semantic_logger.rbs +4 -0
 - metadata +98 -54
 - data/lib/redis_queued_locks/acquier/acquire_lock/dequeue_from_lock_queue/log_visitor.rb +0 -40
 - data/lib/redis_queued_locks/acquier/acquire_lock/instr_visitor.rb +0 -166
 - data/lib/redis_queued_locks/acquier/acquire_lock/log_visitor.rb +0 -216
 - data/lib/redis_queued_locks/acquier/acquire_lock/try_to_lock/log_visitor.rb +0 -541
 - data/lib/redis_queued_locks/acquier/acquire_lock/yield_expire/log_visitor.rb +0 -76
 - data/lib/redis_queued_locks/acquier.rb +0 -18
 
| 
         @@ -2,7 +2,7 @@ 
     | 
|
| 
       2 
2 
     | 
    
         | 
| 
       3 
3 
     | 
    
         
             
            # @api private
         
     | 
| 
       4 
4 
     | 
    
         
             
            # @since 1.0.0
         
     | 
| 
       5 
     | 
    
         
            -
            module RedisQueuedLocks:: 
     | 
| 
      
 5 
     | 
    
         
            +
            module RedisQueuedLocks::Acquirer::Locks
         
     | 
| 
       6 
6 
     | 
    
         
             
              class << self
         
     | 
| 
       7 
7 
     | 
    
         
             
                # @param redis_client [RedisClient]
         
     | 
| 
       8 
8 
     | 
    
         
             
                # @option scan_size [Integer]
         
     | 
| 
         @@ -50,23 +50,36 @@ module RedisQueuedLocks::Acquier::Locks 
     | 
|
| 
       50 
50 
     | 
    
         
             
                def extract_locks_info(redis_client, lock_keys)
         
     | 
| 
       51 
51 
     | 
    
         
             
                  # TODO: refactor with RedisQueuedLocks::Acquier::LockInfo
         
     | 
| 
       52 
52 
     | 
    
         
             
                  Set.new.tap do |seeded_locks|
         
     | 
| 
      
 53 
     | 
    
         
            +
                    # rubocop:disable Layout/LineLength
         
     | 
| 
      
 54 
     | 
    
         
            +
                    # @type var seeded_locks: Set[{ lock: String, status: :released|:alive, info: Hash[String,untyped] }]
         
     | 
| 
      
 55 
     | 
    
         
            +
                    # rubocop:enable Layout/LineLength
         
     | 
| 
      
 56 
     | 
    
         
            +
             
     | 
| 
       53 
57 
     | 
    
         
             
                    # Step X: iterate each lock and extract their info
         
     | 
| 
       54 
58 
     | 
    
         
             
                    lock_keys.each do |lock_key|
         
     | 
| 
       55 
59 
     | 
    
         
             
                      # Step 1: extract lock info from redis
         
     | 
| 
      
 60 
     | 
    
         
            +
             
     | 
| 
      
 61 
     | 
    
         
            +
                      # @type var lock_info: Hash[String,String|Float|Integer]
         
     | 
| 
       56 
62 
     | 
    
         
             
                      lock_info = redis_client.pipelined do |pipeline|
         
     | 
| 
       57 
63 
     | 
    
         
             
                        pipeline.call('HGETALL', lock_key)
         
     | 
| 
       58 
64 
     | 
    
         
             
                        pipeline.call('PTTL', lock_key)
         
     | 
| 
       59 
65 
     | 
    
         
             
                      end.yield_self do |result| # Step 2: format the result
         
     | 
| 
       60 
66 
     | 
    
         
             
                        # Step 2.X: lock is released
         
     | 
| 
       61 
67 
     | 
    
         
             
                        if result == nil
         
     | 
| 
       62 
     | 
    
         
            -
                          {}
         
     | 
| 
      
 68 
     | 
    
         
            +
                          {} #: Hash[String,String|Float|Integer]
         
     | 
| 
       63 
69 
     | 
    
         
             
                        else
         
     | 
| 
      
 70 
     | 
    
         
            +
                          # NOTE: the result of MULTI-command is an array of results of each internal command
         
     | 
| 
      
 71 
     | 
    
         
            +
                          #   - result[0] (HGETALL) (Hash<String,String>)
         
     | 
| 
      
 72 
     | 
    
         
            +
                          #     => (will be mutated further with different value types)
         
     | 
| 
      
 73 
     | 
    
         
            +
                          #   - result[1] (PTTL) (Integer)
         
     | 
| 
      
 74 
     | 
    
         
            +
                          #     => (without any mutation, integer is atomic)
         
     | 
| 
      
 75 
     | 
    
         
            +
             
     | 
| 
      
 76 
     | 
    
         
            +
                          # @type var result: [Hash[String,String|Float|Integer],Integer]
         
     | 
| 
       64 
77 
     | 
    
         
             
                          hget_cmd_res = result[0] # NOTE: HGETALL result (hash)
         
     | 
| 
       65 
78 
     | 
    
         
             
                          pttl_cmd_res = result[1] # NOTE: PTTL result (integer)
         
     | 
| 
       66 
79 
     | 
    
         | 
| 
       67 
80 
     | 
    
         
             
                          # Step 2.Y: lock is released
         
     | 
| 
       68 
81 
     | 
    
         
             
                          if hget_cmd_res == {} || pttl_cmd_res == -2 # NOTE: key does not exist
         
     | 
| 
       69 
     | 
    
         
            -
                            {}
         
     | 
| 
      
 82 
     | 
    
         
            +
                            {} #: Hash[String,String|Float|Integer]
         
     | 
| 
       70 
83 
     | 
    
         
             
                          else
         
     | 
| 
       71 
84 
     | 
    
         
             
                            # Step 2.Z: lock is alive => format received info + add additional rem_ttl info
         
     | 
| 
       72 
85 
     | 
    
         
             
                            hget_cmd_res.tap do |lock_data|
         
     | 
| 
         @@ -2,7 +2,7 @@ 
     | 
|
| 
       2 
2 
     | 
    
         | 
| 
       3 
3 
     | 
    
         
             
            # @api private
         
     | 
| 
       4 
4 
     | 
    
         
             
            # @since 1.0.0
         
     | 
| 
       5 
     | 
    
         
            -
            module RedisQueuedLocks:: 
     | 
| 
      
 5 
     | 
    
         
            +
            module RedisQueuedLocks::Acquirer::QueueInfo
         
     | 
| 
       6 
6 
     | 
    
         
             
              class << self
         
     | 
| 
       7 
7 
     | 
    
         
             
                # Returns an information about the required lock queue by the lock name. The result
         
     | 
| 
       8 
8 
     | 
    
         
             
                # represnts the ordered lock request queue that is ordered by score (Redis sets) and shows
         
     | 
| 
         @@ -12,14 +12,15 @@ module RedisQueuedLocks::Acquier::QueueInfo 
     | 
|
| 
       12 
12 
     | 
    
         
             
                #
         
     | 
| 
       13 
13 
     | 
    
         
             
                # @param redis_client [RedisClient]
         
     | 
| 
       14 
14 
     | 
    
         
             
                # @param lock_name [String]
         
     | 
| 
       15 
     | 
    
         
            -
                # @return [Hash<String 
     | 
| 
      
 15 
     | 
    
         
            +
                # @return [Hash<String,Array<Hash<String,String|Numeric>>,NilClass]
         
     | 
| 
       16 
16 
     | 
    
         
             
                #   - `nil` is returned when lock queue does not exist;
         
     | 
| 
       17 
17 
     | 
    
         
             
                #   - result format: {
         
     | 
| 
       18 
18 
     | 
    
         
             
                #     "lock_queue" => "rql:lock_queue:your_lock_name", # lock queue key in redis,
         
     | 
| 
       19 
     | 
    
         
            -
                #     queue 
     | 
| 
       20 
     | 
    
         
            -
                #       { "acq_id" => "rql:acq:123/456/789/987/identity", "score" => 123 },
         
     | 
| 
       21 
     | 
    
         
            -
                #       { "acq_id" => "rql:acq:123/686/789/987/identity", "score" => 456 },
         
     | 
| 
       22 
     | 
    
         
            -
                # 
     | 
| 
      
 19 
     | 
    
         
            +
                #     "queue" => [
         
     | 
| 
      
 20 
     | 
    
         
            +
                #       { "acq_id" => "rql:acq:123/456/789/987/identity", "score" => 123.456 },
         
     | 
| 
      
 21 
     | 
    
         
            +
                #       { "acq_id" => "rql:acq:123/686/789/987/identity", "score" => 456.789 },
         
     | 
| 
      
 22 
     | 
    
         
            +
                #       ...
         
     | 
| 
      
 23 
     | 
    
         
            +
                #     ] # ordered set (by score) with information about an acquirer and their position in queue
         
     | 
| 
       23 
24 
     | 
    
         
             
                #   }
         
     | 
| 
       24 
25 
     | 
    
         
             
                #
         
     | 
| 
       25 
26 
     | 
    
         
             
                # @api private
         
     | 
| 
         @@ -32,6 +33,7 @@ module RedisQueuedLocks::Acquier::QueueInfo 
     | 
|
| 
       32 
33 
     | 
    
         
             
                    pipeline.call('ZRANGE', lock_key_queue, '0', '-1', 'WITHSCORES')
         
     | 
| 
       33 
34 
     | 
    
         
             
                  end
         
     | 
| 
       34 
35 
     | 
    
         | 
| 
      
 36 
     | 
    
         
            +
                  # @type var result: [Integer,Array[[String,Integer|Float]]]
         
     | 
| 
       35 
37 
     | 
    
         
             
                  exists_cmd_res = result[0]
         
     | 
| 
       36 
38 
     | 
    
         
             
                  zrange_cmd_res = result[1]
         
     | 
| 
       37 
39 
     | 
    
         | 
| 
         @@ -2,7 +2,7 @@ 
     | 
|
| 
       2 
2 
     | 
    
         | 
| 
       3 
3 
     | 
    
         
             
            # @api private
         
     | 
| 
       4 
4 
     | 
    
         
             
            # @since 1.0.0
         
     | 
| 
       5 
     | 
    
         
            -
            module RedisQueuedLocks:: 
     | 
| 
      
 5 
     | 
    
         
            +
            module RedisQueuedLocks::Acquirer::Queues
         
     | 
| 
       6 
6 
     | 
    
         
             
              class << self
         
     | 
| 
       7 
7 
     | 
    
         
             
                # @param redis_client [RedisClient]
         
     | 
| 
       8 
8 
     | 
    
         
             
                # @option scan_size [Integer]
         
     | 
| 
         @@ -28,12 +28,14 @@ module RedisQueuedLocks::Acquier::Queues 
     | 
|
| 
       28 
28 
     | 
    
         
             
                # @since 1.0.0
         
     | 
| 
       29 
29 
     | 
    
         
             
                def scan_queues(redis_client, scan_size)
         
     | 
| 
       30 
30 
     | 
    
         
             
                  Set.new.tap do |lock_queues|
         
     | 
| 
      
 31 
     | 
    
         
            +
                    # @type var lock_queues: Set[String]
         
     | 
| 
       31 
32 
     | 
    
         
             
                    redis_client.scan(
         
     | 
| 
       32 
33 
     | 
    
         
             
                      'MATCH',
         
     | 
| 
       33 
34 
     | 
    
         
             
                      RedisQueuedLocks::Resource::LOCK_QUEUE_PATTERN,
         
     | 
| 
       34 
35 
     | 
    
         
             
                      count: scan_size
         
     | 
| 
       35 
36 
     | 
    
         
             
                    ) do |lock_queue|
         
     | 
| 
       36 
37 
     | 
    
         
             
                      # TODO: reduce unnecessary iterations
         
     | 
| 
      
 38 
     | 
    
         
            +
                      # @type var lock_queue: String
         
     | 
| 
       37 
39 
     | 
    
         
             
                      lock_queues.add(lock_queue)
         
     | 
| 
       38 
40 
     | 
    
         
             
                    end
         
     | 
| 
       39 
41 
     | 
    
         
             
                  end
         
     | 
| 
         @@ -49,12 +51,15 @@ module RedisQueuedLocks::Acquier::Queues 
     | 
|
| 
       49 
51 
     | 
    
         
             
                  # TODO: refactor with RedisQueuedLocks::Acquier::QueueInfo
         
     | 
| 
       50 
52 
     | 
    
         
             
                  Set.new.tap do |seeded_queues|
         
     | 
| 
       51 
53 
     | 
    
         
             
                    # Step X: iterate over each lock queue and extract their info
         
     | 
| 
      
 54 
     | 
    
         
            +
                    # @type var seeded_queues: Set[Hash[Symbol,untyped]]
         
     | 
| 
       52 
55 
     | 
    
         
             
                    lock_queues.each do |lock_queue|
         
     | 
| 
       53 
56 
     | 
    
         
             
                      # Step 1: extract lock queue info from reids
         
     | 
| 
       54 
57 
     | 
    
         
             
                      queue_info = redis_client.pipelined do |pipeline|
         
     | 
| 
       55 
58 
     | 
    
         
             
                        pipeline.call('EXISTS', lock_queue)
         
     | 
| 
       56 
59 
     | 
    
         
             
                        pipeline.call('ZRANGE', lock_queue, '0', '-1', 'WITHSCORES')
         
     | 
| 
       57 
60 
     | 
    
         
             
                      end.yield_self do |result| # Step 2: format the result
         
     | 
| 
      
 61 
     | 
    
         
            +
                        # @type var result: [Integer, Array[[String,Float]]]
         
     | 
| 
      
 62 
     | 
    
         
            +
             
     | 
| 
       58 
63 
     | 
    
         
             
                        exists_cmd_res = result[0]
         
     | 
| 
       59 
64 
     | 
    
         
             
                        zrange_cmd_res = result[1]
         
     | 
| 
       60 
65 
     | 
    
         | 
| 
         @@ -62,10 +67,12 @@ module RedisQueuedLocks::Acquier::Queues 
     | 
|
| 
       62 
67 
     | 
    
         
             
                          zrange_cmd_res.map { |val| { 'acq_id' => val[0], 'score' => val[1] } }
         
     | 
| 
       63 
68 
     | 
    
         
             
                        else
         
     | 
| 
       64 
69 
     | 
    
         
             
                          # Step 2.Y: lock queue did not exist during the pipeline invocation
         
     | 
| 
       65 
     | 
    
         
            -
                          []
         
     | 
| 
      
 70 
     | 
    
         
            +
                          [] #: Array[Hash[String,Float]]
         
     | 
| 
       66 
71 
     | 
    
         
             
                        end
         
     | 
| 
       67 
72 
     | 
    
         
             
                      end
         
     | 
| 
       68 
73 
     | 
    
         | 
| 
      
 74 
     | 
    
         
            +
                      # @type var queue_info: Array[Hash[String,Float]]
         
     | 
| 
      
 75 
     | 
    
         
            +
             
     | 
| 
       69 
76 
     | 
    
         
             
                      # Step 3: push the lock queue info to the result store
         
     | 
| 
       70 
77 
     | 
    
         
             
                      seeded_queues << {
         
     | 
| 
       71 
78 
     | 
    
         
             
                        queue: lock_queue,
         
     | 
| 
         @@ -2,7 +2,7 @@ 
     | 
|
| 
       2 
2 
     | 
    
         | 
| 
       3 
3 
     | 
    
         
             
            # @api private
         
     | 
| 
       4 
4 
     | 
    
         
             
            # @since 1.0.0
         
     | 
| 
       5 
     | 
    
         
            -
            module RedisQueuedLocks:: 
     | 
| 
      
 5 
     | 
    
         
            +
            module RedisQueuedLocks::Acquirer::ReleaseAllLocks
         
     | 
| 
       6 
6 
     | 
    
         
             
              # @since 1.0.0
         
     | 
| 
       7 
7 
     | 
    
         
             
              extend RedisQueuedLocks::Utilities
         
     | 
| 
       8 
8 
     | 
    
         | 
| 
         @@ -16,7 +16,7 @@ module RedisQueuedLocks::Acquier::ReleaseAllLocks 
     | 
|
| 
       16 
16 
     | 
    
         
             
                # @param batch_size [Integer]
         
     | 
| 
       17 
17 
     | 
    
         
             
                #   The number of lock keys that should be released in a time.
         
     | 
| 
       18 
18 
     | 
    
         
             
                # @param logger [::Logger,#debug]
         
     | 
| 
       19 
     | 
    
         
            -
                #   - Logger object used from `configuration` layer (see config[ 
     | 
| 
      
 19 
     | 
    
         
            +
                #   - Logger object used from `configuration` layer (see config['logger']);
         
     | 
| 
       20 
20 
     | 
    
         
             
                #   - See RedisQueuedLocks::Logging::VoidLogger for example;
         
     | 
| 
       21 
21 
     | 
    
         
             
                # @param isntrumenter [#notify]
         
     | 
| 
       22 
22 
     | 
    
         
             
                #   See RedisQueuedLocks::Instrument::ActiveSupport for example.
         
     | 
| 
         @@ -26,15 +26,15 @@ module RedisQueuedLocks::Acquier::ReleaseAllLocks 
     | 
|
| 
       26 
26 
     | 
    
         
             
                # @param log_sampling_enabled [Boolean]
         
     | 
| 
       27 
27 
     | 
    
         
             
                #   - enables <log sampling>: only the configured percent of RQL cases will be logged;
         
     | 
| 
       28 
28 
     | 
    
         
             
                #   - disabled by default;
         
     | 
| 
       29 
     | 
    
         
            -
                #   - works in tandem with <config 
     | 
| 
      
 29 
     | 
    
         
            +
                #   - works in tandem with <config['log_sampling_percent']> and <config['log_sampler']>;
         
     | 
| 
       30 
30 
     | 
    
         
             
                # @param log_sampling_percent [Integer]
         
     | 
| 
       31 
31 
     | 
    
         
             
                #   - the percent of cases that should be logged;
         
     | 
| 
       32 
     | 
    
         
            -
                #   - take an effect when <config 
     | 
| 
       33 
     | 
    
         
            -
                #   - works in tandem with <config 
     | 
| 
      
 32 
     | 
    
         
            +
                #   - take an effect when <config['log_sampling_enalbed']> is true;
         
     | 
| 
      
 33 
     | 
    
         
            +
                #   - works in tandem with <config['log_sampling_enabled']> and <config['log_sampler']> configs;
         
     | 
| 
       34 
34 
     | 
    
         
             
                # @param log_sampler [#sampling_happened?,Module<RedisQueuedLocks::Logging::Sampler>]
         
     | 
| 
       35 
35 
     | 
    
         
             
                #   - percent-based log sampler that decides should be RQL case logged or not;
         
     | 
| 
       36 
     | 
    
         
            -
                #   - works in tandem with <config 
     | 
| 
       37 
     | 
    
         
            -
                #     <config 
     | 
| 
      
 36 
     | 
    
         
            +
                #   - works in tandem with <config['log_sampling_enabled']> and
         
     | 
| 
      
 37 
     | 
    
         
            +
                #     <config['log_sampling_percent']> configs;
         
     | 
| 
       38 
38 
     | 
    
         
             
                #   - based on the ultra simple percent-based (weight-based) algorithm that uses
         
     | 
| 
       39 
39 
     | 
    
         
             
                #     SecureRandom.rand method so the algorithm error is ~(0%..13%);
         
     | 
| 
       40 
40 
     | 
    
         
             
                #   - you can provide your own log sampler with bettter algorithm that should realize
         
     | 
| 
         @@ -47,15 +47,16 @@ module RedisQueuedLocks::Acquier::ReleaseAllLocks 
     | 
|
| 
       47 
47 
     | 
    
         
             
                #   - enables <instrumentaion sampling>: only the configured percent
         
     | 
| 
       48 
48 
     | 
    
         
             
                #     of RQL cases will be instrumented;
         
     | 
| 
       49 
49 
     | 
    
         
             
                #   - disabled by default;
         
     | 
| 
       50 
     | 
    
         
            -
                #   - works in tandem with <config 
     | 
| 
      
 50 
     | 
    
         
            +
                #   - works in tandem with <config['instr_sampling_percent']> and <config['instr_sampler']>;
         
     | 
| 
       51 
51 
     | 
    
         
             
                # @param instr_sampling_percent [Integer]
         
     | 
| 
       52 
52 
     | 
    
         
             
                #   - the percent of cases that should be instrumented;
         
     | 
| 
       53 
     | 
    
         
            -
                #   - take an effect when <config 
     | 
| 
       54 
     | 
    
         
            -
                #   - works in tandem with <config 
     | 
| 
      
 53 
     | 
    
         
            +
                #   - take an effect when <config['instr_sampling_enalbed']> is true;
         
     | 
| 
      
 54 
     | 
    
         
            +
                #   - works in tandem with <config['instr_sampling_enabled']>
         
     | 
| 
      
 55 
     | 
    
         
            +
                #     and <config['instr_sampler']> configs;
         
     | 
| 
       55 
56 
     | 
    
         
             
                # @param instr_sampler [#sampling_happened?,Module<RedisQueuedLocks::Instrument::Sampler>]
         
     | 
| 
       56 
57 
     | 
    
         
             
                #   - percent-based log sampler that decides should be RQL case instrumented or not;
         
     | 
| 
       57 
     | 
    
         
            -
                #   - works in tandem with <config 
     | 
| 
       58 
     | 
    
         
            -
                #     <config 
     | 
| 
      
 58 
     | 
    
         
            +
                #   - works in tandem with <config['instr_sampling_enabled']> and
         
     | 
| 
      
 59 
     | 
    
         
            +
                #     <config['instr_sampling_percent']> configs;
         
     | 
| 
       59 
60 
     | 
    
         
             
                #   - based on the ultra simple percent-based (weight-based) algorithm that uses
         
     | 
| 
       60 
61 
     | 
    
         
             
                #     SecureRandom.rand method so the algorithm error is ~(0%..13%);
         
     | 
| 
       61 
62 
     | 
    
         
             
                #   - you can provide your own log sampler with bettter algorithm that should realize
         
     | 
| 
         @@ -65,12 +66,12 @@ module RedisQueuedLocks::Acquier::ReleaseAllLocks 
     | 
|
| 
       65 
66 
     | 
    
         
             
                #   - marks the method that everything should be instrumneted
         
     | 
| 
       66 
67 
     | 
    
         
             
                #     despite the enabled instrumentation sampling;
         
     | 
| 
       67 
68 
     | 
    
         
             
                #   - makes sense when instrumentation sampling is enabled;
         
     | 
| 
       68 
     | 
    
         
            -
                # @return [ 
     | 
| 
      
 69 
     | 
    
         
            +
                # @return [Hash<Symbol,Any>]
         
     | 
| 
       69 
70 
     | 
    
         
             
                #   Format: { ok: true, result: Hash<Symbol,Numeric> }
         
     | 
| 
       70 
71 
     | 
    
         
             
                #
         
     | 
| 
       71 
72 
     | 
    
         
             
                # @api private
         
     | 
| 
       72 
73 
     | 
    
         
             
                # @since 1.0.0
         
     | 
| 
       73 
     | 
    
         
            -
                # @version 1. 
     | 
| 
      
 74 
     | 
    
         
            +
                # @version 1.14.0
         
     | 
| 
       74 
75 
     | 
    
         
             
                def release_all_locks(
         
     | 
| 
       75 
76 
     | 
    
         
             
                  redis,
         
     | 
| 
       76 
77 
     | 
    
         
             
                  batch_size,
         
     | 
| 
         @@ -86,10 +87,14 @@ module RedisQueuedLocks::Acquier::ReleaseAllLocks 
     | 
|
| 
       86 
87 
     | 
    
         
             
                  instr_sampler,
         
     | 
| 
       87 
88 
     | 
    
         
             
                  instr_sample_this
         
     | 
| 
       88 
89 
     | 
    
         
             
                )
         
     | 
| 
       89 
     | 
    
         
            -
                  rel_start_time =  
     | 
| 
       90 
     | 
    
         
            -
                  fully_release_all_locks(redis, batch_size) => { ok:, result: }
         
     | 
| 
      
 90 
     | 
    
         
            +
                  rel_start_time = clock_gettime
         
     | 
| 
      
 91 
     | 
    
         
            +
                  fully_release_all_locks(redis, batch_size) => { ok:, result: } # steep:ignore
         
     | 
| 
      
 92 
     | 
    
         
            +
             
     | 
| 
      
 93 
     | 
    
         
            +
                  # @type var ok: bool
         
     | 
| 
      
 94 
     | 
    
         
            +
                  # @type var result: Hash[Symbol,Integer]
         
     | 
| 
      
 95 
     | 
    
         
            +
             
     | 
| 
       91 
96 
     | 
    
         
             
                  time_at = Time.now.to_f
         
     | 
| 
       92 
     | 
    
         
            -
                  rel_end_time =  
     | 
| 
      
 97 
     | 
    
         
            +
                  rel_end_time = clock_gettime
         
     | 
| 
       93 
98 
     | 
    
         
             
                  rel_time = ((rel_end_time - rel_start_time) / 1_000.0).ceil(2)
         
     | 
| 
       94 
99 
     | 
    
         | 
| 
       95 
100 
     | 
    
         
             
                  instr_sampled = RedisQueuedLocks::Instrument.should_instrument?(
         
     | 
| 
         @@ -107,10 +112,10 @@ module RedisQueuedLocks::Acquier::ReleaseAllLocks 
     | 
|
| 
       107 
112 
     | 
    
         
             
                    })
         
     | 
| 
       108 
113 
     | 
    
         
             
                  end if instr_sampled
         
     | 
| 
       109 
114 
     | 
    
         | 
| 
       110 
     | 
    
         
            -
                   
     | 
| 
      
 115 
     | 
    
         
            +
                  {
         
     | 
| 
       111 
116 
     | 
    
         
             
                    ok: true,
         
     | 
| 
       112 
117 
     | 
    
         
             
                    result: { rel_key_cnt: result[:rel_key_cnt], rel_time: rel_time }
         
     | 
| 
       113 
     | 
    
         
            -
                   
     | 
| 
      
 118 
     | 
    
         
            +
                  }
         
     | 
| 
       114 
119 
     | 
    
         
             
                end
         
     | 
| 
       115 
120 
     | 
    
         | 
| 
       116 
121 
     | 
    
         
             
                private
         
     | 
| 
         @@ -119,7 +124,7 @@ module RedisQueuedLocks::Acquier::ReleaseAllLocks 
     | 
|
| 
       119 
124 
     | 
    
         
             
                #
         
     | 
| 
       120 
125 
     | 
    
         
             
                # @param redis [RedisClient]
         
     | 
| 
       121 
126 
     | 
    
         
             
                # @param batch_size [Integer]
         
     | 
| 
       122 
     | 
    
         
            -
                # @return [ 
     | 
| 
      
 127 
     | 
    
         
            +
                # @return [Hash<Symbol,Boolean|Hash<Symbol,Integer>>]
         
     | 
| 
       123 
128 
     | 
    
         
             
                #   - Exmaple: { ok: true, result: { rel_key_cnt: 12345 } }
         
     | 
| 
       124 
129 
     | 
    
         
             
                #
         
     | 
| 
       125 
130 
     | 
    
         
             
                # @api private
         
     | 
| 
         @@ -149,7 +154,7 @@ module RedisQueuedLocks::Acquier::ReleaseAllLocks 
     | 
|
| 
       149 
154 
     | 
    
         
             
                    end
         
     | 
| 
       150 
155 
     | 
    
         
             
                  end
         
     | 
| 
       151 
156 
     | 
    
         | 
| 
       152 
     | 
    
         
            -
                   
     | 
| 
      
 157 
     | 
    
         
            +
                  { ok: true, result: { rel_key_cnt: result.sum } }
         
     | 
| 
       153 
158 
     | 
    
         
             
                end
         
     | 
| 
       154 
159 
     | 
    
         
             
              end
         
     | 
| 
       155 
160 
     | 
    
         
             
            end
         
     | 
| 
         @@ -2,7 +2,7 @@ 
     | 
|
| 
       2 
2 
     | 
    
         | 
| 
       3 
3 
     | 
    
         
             
            # @api private
         
     | 
| 
       4 
4 
     | 
    
         
             
            # @since 1.0.0
         
     | 
| 
       5 
     | 
    
         
            -
            module RedisQueuedLocks:: 
     | 
| 
      
 5 
     | 
    
         
            +
            module RedisQueuedLocks::Acquirer::ReleaseLock
         
     | 
| 
       6 
6 
     | 
    
         
             
              # @since 1.0.0
         
     | 
| 
       7 
7 
     | 
    
         
             
              extend RedisQueuedLocks::Utilities
         
     | 
| 
       8 
8 
     | 
    
         | 
| 
         @@ -21,20 +21,20 @@ module RedisQueuedLocks::Acquier::ReleaseLock 
     | 
|
| 
       21 
21 
     | 
    
         
             
                # @param isntrumenter [#notify]
         
     | 
| 
       22 
22 
     | 
    
         
             
                #   See RedisQueuedLocks::Instrument::ActiveSupport for example.
         
     | 
| 
       23 
23 
     | 
    
         
             
                # @param logger [::Logger,#debug]
         
     | 
| 
       24 
     | 
    
         
            -
                #   - Logger object used from `configuration` layer (see config[ 
     | 
| 
      
 24 
     | 
    
         
            +
                #   - Logger object used from `configuration` layer (see config['logger']);
         
     | 
| 
       25 
25 
     | 
    
         
             
                #   - See RedisQueuedLocks::Logging::VoidLogger for example;
         
     | 
| 
       26 
26 
     | 
    
         
             
                # @param log_sampling_enabled [Boolean]
         
     | 
| 
       27 
27 
     | 
    
         
             
                #   - enables <log sampling>: only the configured percent of RQL cases will be logged;
         
     | 
| 
       28 
28 
     | 
    
         
             
                #   - disabled by default;
         
     | 
| 
       29 
     | 
    
         
            -
                #   - works in tandem with <config 
     | 
| 
      
 29 
     | 
    
         
            +
                #   - works in tandem with <config['log_sampling_percent']> and <config['log_sampler']>;
         
     | 
| 
       30 
30 
     | 
    
         
             
                # @param log_sampling_percent [Integer]
         
     | 
| 
       31 
31 
     | 
    
         
             
                #   - the percent of cases that should be logged;
         
     | 
| 
       32 
     | 
    
         
            -
                #   - take an effect when <config 
     | 
| 
       33 
     | 
    
         
            -
                #   - works in tandem with <config 
     | 
| 
      
 32 
     | 
    
         
            +
                #   - take an effect when <config['log_sampling_enalbed']> is true;
         
     | 
| 
      
 33 
     | 
    
         
            +
                #   - works in tandem with <config['log_sampling_enabled']> and <config['log_sampler']> configs;
         
     | 
| 
       34 
34 
     | 
    
         
             
                # @param log_sampler [#sampling_happened?,Module<RedisQueuedLocks::Logging::Sampler>]
         
     | 
| 
       35 
35 
     | 
    
         
             
                #   - percent-based log sampler that decides should be RQL case logged or not;
         
     | 
| 
       36 
     | 
    
         
            -
                #   - works in tandem with <config 
     | 
| 
       37 
     | 
    
         
            -
                #     <config 
     | 
| 
      
 36 
     | 
    
         
            +
                #   - works in tandem with <config['log_sampling_enabled']> and
         
     | 
| 
      
 37 
     | 
    
         
            +
                #     <config['log_sampling_percent']> configs;
         
     | 
| 
       38 
38 
     | 
    
         
             
                #   - based on the ultra simple percent-based (weight-based) algorithm that uses
         
     | 
| 
       39 
39 
     | 
    
         
             
                #     SecureRandom.rand method so the algorithm error is ~(0%..13%);
         
     | 
| 
       40 
40 
     | 
    
         
             
                #   - you can provide your own log sampler with bettter algorithm that should realize
         
     | 
| 
         @@ -47,15 +47,16 @@ module RedisQueuedLocks::Acquier::ReleaseLock 
     | 
|
| 
       47 
47 
     | 
    
         
             
                #   - enables <instrumentaion sampling>: only the configured percent
         
     | 
| 
       48 
48 
     | 
    
         
             
                #     of RQL cases will be instrumented;
         
     | 
| 
       49 
49 
     | 
    
         
             
                #   - disabled by default;
         
     | 
| 
       50 
     | 
    
         
            -
                #   - works in tandem with <config 
     | 
| 
      
 50 
     | 
    
         
            +
                #   - works in tandem with <config['instr_sampling_percent']> and <config['instr_sampler']>;
         
     | 
| 
       51 
51 
     | 
    
         
             
                # @param instr_sampling_percent [Integer]
         
     | 
| 
       52 
52 
     | 
    
         
             
                #   - the percent of cases that should be instrumented;
         
     | 
| 
       53 
     | 
    
         
            -
                #   - take an effect when <config 
     | 
| 
       54 
     | 
    
         
            -
                #   - works in tandem with <config 
     | 
| 
      
 53 
     | 
    
         
            +
                #   - take an effect when <config['instr_sampling_enalbed']> is true;
         
     | 
| 
      
 54 
     | 
    
         
            +
                #   - works in tandem with <config['instr_sampling_enabled']>
         
     | 
| 
      
 55 
     | 
    
         
            +
                #     and <config['instr_sampler']> configs;
         
     | 
| 
       55 
56 
     | 
    
         
             
                # @param instr_sampler [#sampling_happened?,Module<RedisQueuedLocks::Instrument::Sampler>]
         
     | 
| 
       56 
57 
     | 
    
         
             
                #   - percent-based log sampler that decides should be RQL case instrumented or not;
         
     | 
| 
       57 
     | 
    
         
            -
                #   - works in tandem with <config 
     | 
| 
       58 
     | 
    
         
            -
                #     <config 
     | 
| 
      
 58 
     | 
    
         
            +
                #   - works in tandem with <config['instr_sampling_enabled']> and
         
     | 
| 
      
 59 
     | 
    
         
            +
                #     <config['instr_sampling_percent']> configs;
         
     | 
| 
       59 
60 
     | 
    
         
             
                #   - based on the ultra simple percent-based (weight-based) algorithm that uses
         
     | 
| 
       60 
61 
     | 
    
         
             
                #     SecureRandom.rand method so the algorithm error is ~(0%..13%);
         
     | 
| 
       61 
62 
     | 
    
         
             
                #   - you can provide your own log sampler with bettter algorithm that should realize
         
     | 
| 
         @@ -65,12 +66,12 @@ module RedisQueuedLocks::Acquier::ReleaseLock 
     | 
|
| 
       65 
66 
     | 
    
         
             
                #   - marks the method that everything should be instrumneted
         
     | 
| 
       66 
67 
     | 
    
         
             
                #     despite the enabled instrumentation sampling;
         
     | 
| 
       67 
68 
     | 
    
         
             
                #   - makes sense when instrumentation sampling is enabled;
         
     | 
| 
       68 
     | 
    
         
            -
                # @return [ 
     | 
| 
      
 69 
     | 
    
         
            +
                # @return [Hash<Symbol,Boolean<Hash<Symbol,Numeric|String|Symbol>>]
         
     | 
| 
       69 
70 
     | 
    
         
             
                #   Format: { ok: true/false, result: Hash<Symbol,Numeric|String|Symbol> }
         
     | 
| 
       70 
71 
     | 
    
         
             
                #
         
     | 
| 
       71 
72 
     | 
    
         
             
                # @api private
         
     | 
| 
       72 
73 
     | 
    
         
             
                # @since 1.0.0
         
     | 
| 
       73 
     | 
    
         
            -
                # @version 1. 
     | 
| 
      
 74 
     | 
    
         
            +
                # @version 1.14.0
         
     | 
| 
       74 
75 
     | 
    
         
             
                # rubocop:disable Metrics/MethodLength
         
     | 
| 
       75 
76 
     | 
    
         
             
                def release_lock(
         
     | 
| 
       76 
77 
     | 
    
         
             
                  redis,
         
     | 
| 
         @@ -89,10 +90,14 @@ module RedisQueuedLocks::Acquier::ReleaseLock 
     | 
|
| 
       89 
90 
     | 
    
         
             
                  lock_key = RedisQueuedLocks::Resource.prepare_lock_key(lock_name)
         
     | 
| 
       90 
91 
     | 
    
         
             
                  lock_key_queue = RedisQueuedLocks::Resource.prepare_lock_queue(lock_name)
         
     | 
| 
       91 
92 
     | 
    
         | 
| 
       92 
     | 
    
         
            -
                  rel_start_time =  
     | 
| 
       93 
     | 
    
         
            -
                  fully_release_lock(redis, lock_key, lock_key_queue) => { ok:, result: }
         
     | 
| 
      
 93 
     | 
    
         
            +
                  rel_start_time = clock_gettime
         
     | 
| 
      
 94 
     | 
    
         
            +
                  fully_release_lock(redis, lock_key, lock_key_queue) => { ok:, result: } # steep:ignore
         
     | 
| 
      
 95 
     | 
    
         
            +
             
     | 
| 
      
 96 
     | 
    
         
            +
                  # @type var ok: bool
         
     | 
| 
      
 97 
     | 
    
         
            +
                  # @type var result: Hash[Symbol,Symbol]
         
     | 
| 
      
 98 
     | 
    
         
            +
             
     | 
| 
       94 
99 
     | 
    
         
             
                  time_at = Time.now.to_f
         
     | 
| 
       95 
     | 
    
         
            -
                  rel_end_time =  
     | 
| 
      
 100 
     | 
    
         
            +
                  rel_end_time = clock_gettime
         
     | 
| 
       96 
101 
     | 
    
         
             
                  rel_time = ((rel_end_time - rel_start_time) / 1_000.0).ceil(2)
         
     | 
| 
       97 
102 
     | 
    
         | 
| 
       98 
103 
     | 
    
         
             
                  instr_sampled = RedisQueuedLocks::Instrument.should_instrument?(
         
     | 
| 
         @@ -111,7 +116,7 @@ module RedisQueuedLocks::Acquier::ReleaseLock 
     | 
|
| 
       111 
116 
     | 
    
         
             
                    })
         
     | 
| 
       112 
117 
     | 
    
         
             
                  end if instr_sampled
         
     | 
| 
       113 
118 
     | 
    
         | 
| 
       114 
     | 
    
         
            -
                   
     | 
| 
      
 119 
     | 
    
         
            +
                  {
         
     | 
| 
       115 
120 
     | 
    
         
             
                    ok: true,
         
     | 
| 
       116 
121 
     | 
    
         
             
                    result: {
         
     | 
| 
       117 
122 
     | 
    
         
             
                      rel_time: rel_time,
         
     | 
| 
         @@ -120,7 +125,7 @@ module RedisQueuedLocks::Acquier::ReleaseLock 
     | 
|
| 
       120 
125 
     | 
    
         
             
                      queue_res: result[:queue],
         
     | 
| 
       121 
126 
     | 
    
         
             
                      lock_res: result[:lock]
         
     | 
| 
       122 
127 
     | 
    
         
             
                    }
         
     | 
| 
       123 
     | 
    
         
            -
                   
     | 
| 
      
 128 
     | 
    
         
            +
                  }
         
     | 
| 
       124 
129 
     | 
    
         
             
                end
         
     | 
| 
       125 
130 
     | 
    
         
             
                # rubocop:enable Metrics/MethodLength
         
     | 
| 
       126 
131 
     | 
    
         | 
| 
         @@ -131,7 +136,7 @@ module RedisQueuedLocks::Acquier::ReleaseLock 
     | 
|
| 
       131 
136 
     | 
    
         
             
                # @param redis [RedisClient]
         
     | 
| 
       132 
137 
     | 
    
         
             
                # @param lock_key [String]
         
     | 
| 
       133 
138 
     | 
    
         
             
                # @param lock_key_queue [String]
         
     | 
| 
       134 
     | 
    
         
            -
                # @return [ 
     | 
| 
      
 139 
     | 
    
         
            +
                # @return [Hash<Symbol,Boolean|Hash<Symbol,Symbol>>]
         
     | 
| 
       135 
140 
     | 
    
         
             
                #   Format: {
         
     | 
| 
       136 
141 
     | 
    
         
             
                #     ok: true/false,
         
     | 
| 
       137 
142 
     | 
    
         
             
                #     result: {
         
     | 
| 
         @@ -143,6 +148,7 @@ module RedisQueuedLocks::Acquier::ReleaseLock 
     | 
|
| 
       143 
148 
     | 
    
         
             
                # @api private
         
     | 
| 
       144 
149 
     | 
    
         
             
                # @since 1.0.0
         
     | 
| 
       145 
150 
     | 
    
         
             
                def fully_release_lock(redis, lock_key, lock_key_queue)
         
     | 
| 
      
 151 
     | 
    
         
            +
                  # @type var result: [Integer,Integer]
         
     | 
| 
       146 
152 
     | 
    
         
             
                  result = redis.with do |rconn|
         
     | 
| 
       147 
153 
     | 
    
         
             
                    rconn.multi do |transact|
         
     | 
| 
       148 
154 
     | 
    
         
             
                      transact.call('ZREMRANGEBYSCORE', lock_key_queue, '-inf', '+inf')
         
     | 
| 
         @@ -150,13 +156,13 @@ module RedisQueuedLocks::Acquier::ReleaseLock 
     | 
|
| 
       150 
156 
     | 
    
         
             
                    end
         
     | 
| 
       151 
157 
     | 
    
         
             
                  end
         
     | 
| 
       152 
158 
     | 
    
         | 
| 
       153 
     | 
    
         
            -
                   
     | 
| 
      
 159 
     | 
    
         
            +
                  {
         
     | 
| 
       154 
160 
     | 
    
         
             
                    ok: true,
         
     | 
| 
       155 
161 
     | 
    
         
             
                    result: {
         
     | 
| 
       156 
162 
     | 
    
         
             
                      queue: (result[0] != 0) ? :released : :nothing_to_release,
         
     | 
| 
       157 
163 
     | 
    
         
             
                      lock: (result[1] != 0) ? :released : :nothing_to_release
         
     | 
| 
       158 
164 
     | 
    
         
             
                    }
         
     | 
| 
       159 
     | 
    
         
            -
                   
     | 
| 
      
 165 
     | 
    
         
            +
                  }
         
     | 
| 
       160 
166 
     | 
    
         
             
                end
         
     | 
| 
       161 
167 
     | 
    
         
             
              end
         
     | 
| 
       162 
168 
     | 
    
         
             
            end
         
     | 
| 
         @@ -0,0 +1,211 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            # frozen_string_literal: true
         
     | 
| 
      
 2 
     | 
    
         
            +
             
     | 
| 
      
 3 
     | 
    
         
            +
            # @api private
         
     | 
| 
      
 4 
     | 
    
         
            +
            # @since 1.14.0
         
     | 
| 
      
 5 
     | 
    
         
            +
            module RedisQueuedLocks::Acquirer::ReleaseLocksOf
         
     | 
| 
      
 6 
     | 
    
         
            +
              # @since 1.14.0
         
     | 
| 
      
 7 
     | 
    
         
            +
              extend RedisQueuedLocks::Utilities
         
     | 
| 
      
 8 
     | 
    
         
            +
             
     | 
| 
      
 9 
     | 
    
         
            +
              class << self
         
     | 
| 
      
 10 
     | 
    
         
            +
                # Release all queues and locks that belong to the given host and its associated acquirer.
         
     | 
| 
      
 11 
     | 
    
         
            +
                #
         
     | 
| 
      
 12 
     | 
    
         
            +
                # @param refused_host_id [String]
         
     | 
| 
      
 13 
     | 
    
         
            +
                #   A host whose locks and queues should be released.
         
     | 
| 
      
 14 
     | 
    
         
            +
                # @param refused_acquirer_id [String]
         
     | 
| 
      
 15 
     | 
    
         
            +
                #   An acquirer (of the passed host) whose locks and queues should be released.
         
     | 
| 
      
 16 
     | 
    
         
            +
                # @param redis [RedisClient]
         
     | 
| 
      
 17 
     | 
    
         
            +
                #   Redis connection client.
         
     | 
| 
      
 18 
     | 
    
         
            +
                # @param lock_scan_size [Integer]
         
     | 
| 
      
 19 
     | 
    
         
            +
                #   The number of lock keys that should be released in a time.
         
     | 
| 
      
 20 
     | 
    
         
            +
                #   Affects the RubyVM memmory (cuz each found lock will be temporary stored in memory for
         
     | 
| 
      
 21 
     | 
    
         
            +
                #   subsequent removal from redis in one query at a time).
         
     | 
| 
      
 22 
     | 
    
         
            +
                # @param queue_scan_size [Integer]
         
     | 
| 
      
 23 
     | 
    
         
            +
                #   The number of lock queues that should be scanned removing an acquirer from them (at a time).
         
     | 
| 
      
 24 
     | 
    
         
            +
                # @param logger [::Logger,#debug]
         
     | 
| 
      
 25 
     | 
    
         
            +
                #   - Logger object used from `configuration` layer (see config['logger']);
         
     | 
| 
      
 26 
     | 
    
         
            +
                #   - See RedisQueuedLocks::Logging::VoidLogger for example;
         
     | 
| 
      
 27 
     | 
    
         
            +
                # @param isntrumenter [#notify]
         
     | 
| 
      
 28 
     | 
    
         
            +
                #   See RedisQueuedLocks::Instrument::ActiveSupport for example.
         
     | 
| 
      
 29 
     | 
    
         
            +
                # @param instrument [NilClass,Any]
         
     | 
| 
      
 30 
     | 
    
         
            +
                #    - Custom instrumentation data wich will be passed to the instrumenter's payload
         
     | 
| 
      
 31 
     | 
    
         
            +
                #      with :instrument key;
         
     | 
| 
      
 32 
     | 
    
         
            +
                # @param log_sampling_enabled [Boolean]
         
     | 
| 
      
 33 
     | 
    
         
            +
                #   - enables <log sampling>: only the configured percent of RQL cases will be logged;
         
     | 
| 
      
 34 
     | 
    
         
            +
                #   - disabled by default;
         
     | 
| 
      
 35 
     | 
    
         
            +
                #   - works in tandem with <config['log_sampling_percent']> and <config['log_sampler']>;
         
     | 
| 
      
 36 
     | 
    
         
            +
                # @param log_sampling_percent [Integer]
         
     | 
| 
      
 37 
     | 
    
         
            +
                #   - the percent of cases that should be logged;
         
     | 
| 
      
 38 
     | 
    
         
            +
                #   - take an effect when <config['log_sampling_enalbed']> is true;
         
     | 
| 
      
 39 
     | 
    
         
            +
                #   - works in tandem with <config['log_sampling_enabled']> and <config['log_sampler']> configs;
         
     | 
| 
      
 40 
     | 
    
         
            +
                # @param log_sampler [#sampling_happened?,Module<RedisQueuedLocks::Logging::Sampler>]
         
     | 
| 
      
 41 
     | 
    
         
            +
                #   - percent-based log sampler that decides should be RQL case logged or not;
         
     | 
| 
      
 42 
     | 
    
         
            +
                #   - works in tandem with <config['log_sampling_enabled']> and
         
     | 
| 
      
 43 
     | 
    
         
            +
                #     <config['log_sampling_percent']> configs;
         
     | 
| 
      
 44 
     | 
    
         
            +
                #   - based on the ultra simple percent-based (weight-based) algorithm that uses
         
     | 
| 
      
 45 
     | 
    
         
            +
                #     SecureRandom.rand method so the algorithm error is ~(0%..13%);
         
     | 
| 
      
 46 
     | 
    
         
            +
                #   - you can provide your own log sampler with bettter algorithm that should realize
         
     | 
| 
      
 47 
     | 
    
         
            +
                #     `sampling_happened?(percent) => boolean` interface
         
     | 
| 
      
 48 
     | 
    
         
            +
                #     (see `RedisQueuedLocks::Logging::Sampler` for example);
         
     | 
| 
      
 49 
     | 
    
         
            +
                # @param log_sample_this [Boolean]
         
     | 
| 
      
 50 
     | 
    
         
            +
                #   - marks the method that everything should be logged despite the enabled log sampling;
         
     | 
| 
      
 51 
     | 
    
         
            +
                #   - makes sense when log sampling is enabled;
         
     | 
| 
      
 52 
     | 
    
         
            +
                # @param instr_sampling_enabled [Boolean]
         
     | 
| 
      
 53 
     | 
    
         
            +
                #   - enables <instrumentaion sampling>: only the configured percent
         
     | 
| 
      
 54 
     | 
    
         
            +
                #     of RQL cases will be instrumented;
         
     | 
| 
      
 55 
     | 
    
         
            +
                #   - disabled by default;
         
     | 
| 
      
 56 
     | 
    
         
            +
                #   - works in tandem with <config['instr_sampling_percent']> and <config['instr_sampler']>;
         
     | 
| 
      
 57 
     | 
    
         
            +
                # @param instr_sampling_percent [Integer]
         
     | 
| 
      
 58 
     | 
    
         
            +
                #   - the percent of cases that should be instrumented;
         
     | 
| 
      
 59 
     | 
    
         
            +
                #   - take an effect when <config['instr_sampling_enalbed']> is true;
         
     | 
| 
      
 60 
     | 
    
         
            +
                #   - works in tandem with <config['instr_sampling_enabled']>
         
     | 
| 
      
 61 
     | 
    
         
            +
                #     and <config['instr_sampler']> configs;
         
     | 
| 
      
 62 
     | 
    
         
            +
                # @param instr_sampler [#sampling_happened?,Module<RedisQueuedLocks::Instrument::Sampler>]
         
     | 
| 
      
 63 
     | 
    
         
            +
                #   - percent-based log sampler that decides should be RQL case instrumented or not;
         
     | 
| 
      
 64 
     | 
    
         
            +
                #   - works in tandem with <config['instr_sampling_enabled']> and
         
     | 
| 
      
 65 
     | 
    
         
            +
                #     <config['instr_sampling_percent']> configs;
         
     | 
| 
      
 66 
     | 
    
         
            +
                #   - based on the ultra simple percent-based (weight-based) algorithm that uses
         
     | 
| 
      
 67 
     | 
    
         
            +
                #     SecureRandom.rand method so the algorithm error is ~(0%..13%);
         
     | 
| 
      
 68 
     | 
    
         
            +
                #   - you can provide your own log sampler with bettter algorithm that should realize
         
     | 
| 
      
 69 
     | 
    
         
            +
                #     `sampling_happened?(percent) => boolean` interface
         
     | 
| 
      
 70 
     | 
    
         
            +
                #     (see `RedisQueuedLocks::Instrument::Sampler` for example);
         
     | 
| 
      
 71 
     | 
    
         
            +
                # @param instr_sample_this [Boolean]
         
     | 
| 
      
 72 
     | 
    
         
            +
                #   - marks the method that everything should be instrumneted
         
     | 
| 
      
 73 
     | 
    
         
            +
                #     despite the enabled instrumentation sampling;
         
     | 
| 
      
 74 
     | 
    
         
            +
                #   - makes sense when instrumentation sampling is enabled;
         
     | 
| 
      
 75 
     | 
    
         
            +
                # @return [Hash<Symbol,Any>]
         
     | 
| 
      
 76 
     | 
    
         
            +
                #   Format: { ok: true, result: Hash<Symbol,Numeric> }
         
     | 
| 
      
 77 
     | 
    
         
            +
                #
         
     | 
| 
      
 78 
     | 
    
         
            +
                # @api private
         
     | 
| 
      
 79 
     | 
    
         
            +
                # @since 1.14.0
         
     | 
| 
      
 80 
     | 
    
         
            +
                # rubocop:disable Metrics/MethodLength
         
     | 
| 
      
 81 
     | 
    
         
            +
                def release_locks_of(
         
     | 
| 
      
 82 
     | 
    
         
            +
                  refused_host_id,
         
     | 
| 
      
 83 
     | 
    
         
            +
                  refused_acquirer_id,
         
     | 
| 
      
 84 
     | 
    
         
            +
                  redis,
         
     | 
| 
      
 85 
     | 
    
         
            +
                  lock_scan_size,
         
     | 
| 
      
 86 
     | 
    
         
            +
                  queue_scan_size,
         
     | 
| 
      
 87 
     | 
    
         
            +
                  logger,
         
     | 
| 
      
 88 
     | 
    
         
            +
                  instrumenter,
         
     | 
| 
      
 89 
     | 
    
         
            +
                  instrument,
         
     | 
| 
      
 90 
     | 
    
         
            +
                  log_sampling_enabled,
         
     | 
| 
      
 91 
     | 
    
         
            +
                  log_sampling_percent,
         
     | 
| 
      
 92 
     | 
    
         
            +
                  log_sampler,
         
     | 
| 
      
 93 
     | 
    
         
            +
                  log_sample_this,
         
     | 
| 
      
 94 
     | 
    
         
            +
                  instr_sampling_enabled,
         
     | 
| 
      
 95 
     | 
    
         
            +
                  instr_sampling_percent,
         
     | 
| 
      
 96 
     | 
    
         
            +
                  instr_sampler,
         
     | 
| 
      
 97 
     | 
    
         
            +
                  instr_sample_this
         
     | 
| 
      
 98 
     | 
    
         
            +
                ) # TODO: move from SCAN to indexes :thinking:
         
     | 
| 
      
 99 
     | 
    
         
            +
                  rel_start_time = clock_gettime
         
     | 
| 
      
 100 
     | 
    
         
            +
             
     | 
| 
      
 101 
     | 
    
         
            +
                  # steep:ignore:start
         
     | 
| 
      
 102 
     | 
    
         
            +
                  fully_release_locks_of(
         
     | 
| 
      
 103 
     | 
    
         
            +
                    refused_host_id,
         
     | 
| 
      
 104 
     | 
    
         
            +
                    refused_acquirer_id,
         
     | 
| 
      
 105 
     | 
    
         
            +
                    redis,
         
     | 
| 
      
 106 
     | 
    
         
            +
                    lock_scan_size,
         
     | 
| 
      
 107 
     | 
    
         
            +
                    queue_scan_size
         
     | 
| 
      
 108 
     | 
    
         
            +
                  ) => { ok:, result: }
         
     | 
| 
      
 109 
     | 
    
         
            +
                  # steep:ignore:end
         
     | 
| 
      
 110 
     | 
    
         
            +
             
     | 
| 
      
 111 
     | 
    
         
            +
                  # @type var ok: bool
         
     | 
| 
      
 112 
     | 
    
         
            +
                  # @type var result: Hash[Symbol,Integer]
         
     | 
| 
      
 113 
     | 
    
         
            +
             
     | 
| 
      
 114 
     | 
    
         
            +
                  time_at = Time.now.to_f
         
     | 
| 
      
 115 
     | 
    
         
            +
                  rel_end_time = clock_gettime
         
     | 
| 
      
 116 
     | 
    
         
            +
                  rel_time = ((rel_end_time - rel_start_time) / 1_000.0).ceil(2)
         
     | 
| 
      
 117 
     | 
    
         
            +
             
     | 
| 
      
 118 
     | 
    
         
            +
                  instr_sampled = RedisQueuedLocks::Instrument.should_instrument?(
         
     | 
| 
      
 119 
     | 
    
         
            +
                    instr_sampling_enabled,
         
     | 
| 
      
 120 
     | 
    
         
            +
                    instr_sample_this,
         
     | 
| 
      
 121 
     | 
    
         
            +
                    instr_sampling_percent,
         
     | 
| 
      
 122 
     | 
    
         
            +
                    instr_sampler
         
     | 
| 
      
 123 
     | 
    
         
            +
                  )
         
     | 
| 
      
 124 
     | 
    
         
            +
             
     | 
| 
      
 125 
     | 
    
         
            +
                  run_non_critical do
         
     | 
| 
      
 126 
     | 
    
         
            +
                    instrumenter.notify('redis_queued_locks.release_locks_of', {
         
     | 
| 
      
 127 
     | 
    
         
            +
                      at: time_at,
         
     | 
| 
      
 128 
     | 
    
         
            +
                      rel_time: rel_time,
         
     | 
| 
      
 129 
     | 
    
         
            +
                      rel_key_cnt: result[:rel_key_cnt],
         
     | 
| 
      
 130 
     | 
    
         
            +
                      tch_queue_cnt: result[:tch_queue_cnt]
         
     | 
| 
      
 131 
     | 
    
         
            +
                    })
         
     | 
| 
      
 132 
     | 
    
         
            +
                  end if instr_sampled
         
     | 
| 
      
 133 
     | 
    
         
            +
             
     | 
| 
      
 134 
     | 
    
         
            +
                  {
         
     | 
| 
      
 135 
     | 
    
         
            +
                    ok: true,
         
     | 
| 
      
 136 
     | 
    
         
            +
                    result: {
         
     | 
| 
      
 137 
     | 
    
         
            +
                      rel_key_cnt: result[:rel_key_cnt],
         
     | 
| 
      
 138 
     | 
    
         
            +
                      tch_queue_cnt: result[:tch_queue_cnt],
         
     | 
| 
      
 139 
     | 
    
         
            +
                      rel_time: rel_time
         
     | 
| 
      
 140 
     | 
    
         
            +
                    }
         
     | 
| 
      
 141 
     | 
    
         
            +
                  }
         
     | 
| 
      
 142 
     | 
    
         
            +
                end
         
     | 
| 
      
 143 
     | 
    
         
            +
                # rubocop:enable Metrics/MethodLength
         
     | 
| 
      
 144 
     | 
    
         
            +
             
     | 
| 
      
 145 
     | 
    
         
            +
                private
         
     | 
| 
      
 146 
     | 
    
         
            +
             
     | 
| 
      
 147 
     | 
    
         
            +
                # @param refused_host_id [String]
         
     | 
| 
      
 148 
     | 
    
         
            +
                # @param refused_acquirer_id [String]
         
     | 
| 
      
 149 
     | 
    
         
            +
                # @param redis [RedisClient]
         
     | 
| 
      
 150 
     | 
    
         
            +
                # @param lock_scan_size [Integer]
         
     | 
| 
      
 151 
     | 
    
         
            +
                # @param queue_scan_size [Integer]
         
     | 
| 
      
 152 
     | 
    
         
            +
                # @return [Hash<Symbol,Boolean|Hash<Symbol,Integer>>]
         
     | 
| 
      
 153 
     | 
    
         
            +
                #   - Example: { ok: true, result: { rel_key_cnt: 12345, tch_queue_cnt: 321 } }
         
     | 
| 
      
 154 
     | 
    
         
            +
                #
         
     | 
| 
      
 155 
     | 
    
         
            +
                # @api private
         
     | 
| 
      
 156 
     | 
    
         
            +
                # @since 1.14.0
         
     | 
| 
      
 157 
     | 
    
         
            +
                # rubocop:disable Metrics/MethodLength
         
     | 
| 
      
 158 
     | 
    
         
            +
                def fully_release_locks_of(
         
     | 
| 
      
 159 
     | 
    
         
            +
                  refused_host_id,
         
     | 
| 
      
 160 
     | 
    
         
            +
                  refused_acquirer_id,
         
     | 
| 
      
 161 
     | 
    
         
            +
                  redis,
         
     | 
| 
      
 162 
     | 
    
         
            +
                  lock_scan_size,
         
     | 
| 
      
 163 
     | 
    
         
            +
                  queue_scan_size
         
     | 
| 
      
 164 
     | 
    
         
            +
                )
         
     | 
| 
      
 165 
     | 
    
         
            +
                  # TODO: some indexing approach isntead of <scan>
         
     | 
| 
      
 166 
     | 
    
         
            +
                  rel_key_cnt = 0
         
     | 
| 
      
 167 
     | 
    
         
            +
                  tch_queue_cnt = 0
         
     | 
| 
      
 168 
     | 
    
         
            +
             
     | 
| 
      
 169 
     | 
    
         
            +
                  redis.with do |rconn|
         
     | 
| 
      
 170 
     | 
    
         
            +
                    # Step A: drop locks of the passed host/acquirer
         
     | 
| 
      
 171 
     | 
    
         
            +
                    refused_locks = Set.new #: Set[String]
         
     | 
| 
      
 172 
     | 
    
         
            +
                    rconn.scan(
         
     | 
| 
      
 173 
     | 
    
         
            +
                      'MATCH',
         
     | 
| 
      
 174 
     | 
    
         
            +
                      RedisQueuedLocks::Resource::LOCK_PATTERN,
         
     | 
| 
      
 175 
     | 
    
         
            +
                      count: lock_scan_size
         
     | 
| 
      
 176 
     | 
    
         
            +
                    ) do |lock_key|
         
     | 
| 
      
 177 
     | 
    
         
            +
                      acquirer_id, host_id = rconn.call('HMGET', lock_key, 'acq_id', 'hst_id')
         
     | 
| 
      
 178 
     | 
    
         
            +
                      if refused_host_id == host_id && refused_acquirer_id == acquirer_id
         
     | 
| 
      
 179 
     | 
    
         
            +
                        refused_locks << lock_key
         
     | 
| 
      
 180 
     | 
    
         
            +
                      end
         
     | 
| 
      
 181 
     | 
    
         
            +
             
     | 
| 
      
 182 
     | 
    
         
            +
                      if refused_locks.size >= lock_scan_size
         
     | 
| 
      
 183 
     | 
    
         
            +
                        # NOTE: steep can not recognize the `*`-splat operator on Set objects
         
     | 
| 
      
 184 
     | 
    
         
            +
                        rconn.call('DEL', *refused_locks) # steep:ignore
         
     | 
| 
      
 185 
     | 
    
         
            +
                        rel_key_cnt += refused_locks.size
         
     | 
| 
      
 186 
     | 
    
         
            +
                        refused_locks.clear
         
     | 
| 
      
 187 
     | 
    
         
            +
                      end
         
     | 
| 
      
 188 
     | 
    
         
            +
                    end
         
     | 
| 
      
 189 
     | 
    
         
            +
             
     | 
| 
      
 190 
     | 
    
         
            +
                    if refused_locks.any?
         
     | 
| 
      
 191 
     | 
    
         
            +
                      # NOTE: steep can not recognize the `*`-splat operator on Set objects
         
     | 
| 
      
 192 
     | 
    
         
            +
                      rconn.call('DEL', *refused_locks) # steep:ignore
         
     | 
| 
      
 193 
     | 
    
         
            +
                      rel_key_cnt += refused_locks.size
         
     | 
| 
      
 194 
     | 
    
         
            +
                    end
         
     | 
| 
      
 195 
     | 
    
         
            +
             
     | 
| 
      
 196 
     | 
    
         
            +
                    # Step B: drop passed host/acquirer from lock queues
         
     | 
| 
      
 197 
     | 
    
         
            +
                    rconn.scan(
         
     | 
| 
      
 198 
     | 
    
         
            +
                      'MATCH',
         
     | 
| 
      
 199 
     | 
    
         
            +
                      RedisQueuedLocks::Resource::LOCK_QUEUE_PATTERN,
         
     | 
| 
      
 200 
     | 
    
         
            +
                      count: queue_scan_size
         
     | 
| 
      
 201 
     | 
    
         
            +
                    ) do |lock_queue|
         
     | 
| 
      
 202 
     | 
    
         
            +
                      res = rconn.call('ZREM', lock_queue, refused_acquirer_id)
         
     | 
| 
      
 203 
     | 
    
         
            +
                      tch_queue_cnt += 1 if res != 0
         
     | 
| 
      
 204 
     | 
    
         
            +
                    end
         
     | 
| 
      
 205 
     | 
    
         
            +
                  end
         
     | 
| 
      
 206 
     | 
    
         
            +
             
     | 
| 
      
 207 
     | 
    
         
            +
                  { ok: true, result: { rel_key_cnt:, tch_queue_cnt: } }
         
     | 
| 
      
 208 
     | 
    
         
            +
                end
         
     | 
| 
      
 209 
     | 
    
         
            +
              end
         
     | 
| 
      
 210 
     | 
    
         
            +
              # rubocop:enable Metrics/MethodLength
         
     | 
| 
      
 211 
     | 
    
         
            +
            end
         
     | 
| 
         @@ -0,0 +1,19 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            # frozen_string_literal: true
         
     | 
| 
      
 2 
     | 
    
         
            +
             
     | 
| 
      
 3 
     | 
    
         
            +
            # @api private
         
     | 
| 
      
 4 
     | 
    
         
            +
            # @since 1.0.0
         
     | 
| 
      
 5 
     | 
    
         
            +
            module RedisQueuedLocks::Acquirer
         
     | 
| 
      
 6 
     | 
    
         
            +
              require_relative 'acquirer/acquire_lock'
         
     | 
| 
      
 7 
     | 
    
         
            +
              require_relative 'acquirer/release_lock'
         
     | 
| 
      
 8 
     | 
    
         
            +
              require_relative 'acquirer/release_all_locks'
         
     | 
| 
      
 9 
     | 
    
         
            +
              require_relative 'acquirer/release_locks_of'
         
     | 
| 
      
 10 
     | 
    
         
            +
              require_relative 'acquirer/is_locked'
         
     | 
| 
      
 11 
     | 
    
         
            +
              require_relative 'acquirer/is_queued'
         
     | 
| 
      
 12 
     | 
    
         
            +
              require_relative 'acquirer/lock_info'
         
     | 
| 
      
 13 
     | 
    
         
            +
              require_relative 'acquirer/queue_info'
         
     | 
| 
      
 14 
     | 
    
         
            +
              require_relative 'acquirer/locks'
         
     | 
| 
      
 15 
     | 
    
         
            +
              require_relative 'acquirer/queues'
         
     | 
| 
      
 16 
     | 
    
         
            +
              require_relative 'acquirer/keys'
         
     | 
| 
      
 17 
     | 
    
         
            +
              require_relative 'acquirer/extend_lock_ttl'
         
     | 
| 
      
 18 
     | 
    
         
            +
              require_relative 'acquirer/clear_dead_requests'
         
     | 
| 
      
 19 
     | 
    
         
            +
            end
         
     |