Module: Lockistics

Defined in:
lib/lockistics.rb,
lib/lockistics/lock.rb,
lib/lockistics/meter.rb,
lib/lockistics/version.rb,
lib/lockistics/meterable.rb,
lib/lockistics/statistics.rb,
lib/lockistics/configuration.rb

Overview

Lockistics is basically a distributed mutex on Redis.

In addition to locking it also collects statistics data of the locking events.

You can use each part separately if you just want to collect statistics or to do simple locking.

Total, daily and hourly metrics you get for each key are:

- Number of locks
- Number of times having to wait for lock
- Number of failed locking attempts
- Minimum and maximum duration
- Minimum and maximum memory growth (using OS gem)
- Arbitary metrics you add during execution

Theres also an experimental module you can use to wrap any instance
methods inside a meter block.

@example
  class SomeClass
    include Lockistics::Meterable
    meter :instance_method_name

    def instance_method_name
      do_something
    end
  end

Defined Under Namespace

Modules: Meterable Classes: Configuration, DummyMeter, Lock, LockTimeout, Meter, Statistics

Constant Summary collapse

VERSION =
"0.1.5"

Class Method Summary collapse

Class Method Details

.configurationObject

Returns an instance of Lockistics::Configuration



55
56
57
# File 'lib/lockistics.rb', line 55

def self.configuration
  @configuration ||= Configuration.new
end

.configure {|configuration| ... } ⇒ Object

Configure the gem

Examples:

Lockistics.configure do |config|
  config.redis                = Redis.new
  config.namespace            = "production.locks"
  config.expire               = 300   # seconds
  config.sleep                = 0.5   # seconds to sleep between retries
  config.retries              = 10    # retry times
  config.raise                = true  # raise Lockistics::TimeoutException when lock fails
  config.pass_through         = false # don't do anything, just pass everything through
end

Yields:



50
51
52
# File 'lib/lockistics.rb', line 50

def self.configure(&block)
  yield configuration
end

.known_keys(key = nil) ⇒ Object

Get a list of known keys or add a key to known keys list.



144
145
146
147
148
149
150
# File 'lib/lockistics.rb', line 144

def self.known_keys(key=nil)
  if key.nil?
    redis.smembers "#{Lockistics.configuration.namespace}.known_keys"
  else
    redis.sadd "#{Lockistics.configuration.namespace}.known_keys", key
  end
end

.lock(key, options = {}, &block) ⇒ Object

Get a hold of a lock or wait for it to be released

Given a block, will release the lock after block exection

Examples:

Lockistics.lock("generate-stuff-raketask") do
  doing_some_heavy_stuff
end
or
return nil unless Lockistics.lock("generate-stuff", :wait => false)
or
begin
  Lockistics.lock("stuff") do
    ...
  end
rescue Lockistics::Timeout
  ...
end


82
83
84
85
86
87
88
# File 'lib/lockistics.rb', line 82

def self.lock(key, options={}, &block)
  if block_given?
    Meter.new(key, options.merge(:no_metrics => true)).perform(&block)
  else
    Lock.new(key, options).acquire_lock
  end
end

.meter(key, options = {}, &block) ⇒ Object

Don’t perform locking, just collect metrics.

Examples:

Lockistics.meter("generate-stuff") do |meter|
  do_stuff
  meter.incrby :stuffs_generated, 50
end


97
98
99
# File 'lib/lockistics.rb', line 97

def self.meter(key, options={}, &block)
  Meter.new(key, options.merge(:lock => nil)).perform(&block)
end

.meterlock(key, options = {}, &block) ⇒ Object

Perform locking and statistics collection

Examples:

Lockistics.meterlock("generate-stuff") do |meter|
  results = do_stuff
  if results.empty?
    meter.incr "empty_results"
  else
    meter.incrby "stuffs_done", results.size
  end
end


112
113
114
# File 'lib/lockistics.rb', line 112

def self.meterlock(key, options={}, &block)
  Meter.new(key, options.merge(:lock => Lock.new(key, options))).perform(&block)
end

.redisObject

Accessor to the redis configured via Lockistics::Configuration



60
61
62
# File 'lib/lockistics.rb', line 60

def self.redis
  configuration.redis
end

.release(key, options = {}) ⇒ Object

Manually release a lock

Examples:

Lockistics.release("generate-stuff")
or
lock = Lockistics.lock("generate-stuff", :wait => false)
if lock.acquire_lock
  do_some_stuff
  lock.release_lock
end


126
127
128
# File 'lib/lockistics.rb', line 126

def self.release(key, options={})
  Lock.new(key).release_lock
end

.statistics(key) ⇒ Object

Returns an instance of Lockistics::Statistics for the key.

Examples:

stats = Lockistics.statistics('generate-stuff')
stats.last_run
  => Mon May 19 16:38:52 +0300 2014
stats.total
  => {"invocations" => 50, ...}


138
139
140
# File 'lib/lockistics.rb', line 138

def self.statistics(key)
  Statistics.new(key)
end