Class: ZK::Locker::LockerBase
- Inherits:
-
Object
- Object
- ZK::Locker::LockerBase
- Includes:
- Exceptions, ZK::Logging
- Defined in:
- lib/zk/locker/locker_base.rb
Overview
Common code for the shared and exclusive lock implementations
One thing to note about this implementation is that the API unfortunately does not follow the convention where bang ('!') methods raise exceptions when they fail. This was an oversight on the part of the author, and it may be corrected sometime in the future.
Direct Known Subclasses
Instance Attribute Summary collapse
-
#lock_path ⇒ String
readonly
our absolute lock node path.
Instance Method Summary collapse
-
#acquirable? ⇒ Boolean
- If this instance holds the lock is true we return true (as we have already succeeded in acquiring the lock) * If this instance doesn't hold the lock, we'll do a check on the server to see if there are any participants who hold the lock and would prevent us from acquiring the lock.
-
#assert! ⇒ Object
This is for users who wish to check that the assumption is correct that they actually still hold the lock.
-
#initialize(client, name, root_lock_node = nil) ⇒ LockerBase
constructor
Create a new lock instance.
- #lock(blocking = false) ⇒ true, ...
-
#lock!(blocking = false) ⇒ true, ...
deprecated
Deprecated.
the use of lock! is deprecated and may be removed or have its semantics changed in a future release
-
#lock_basename ⇒ nil, String
the basename of our lock path.
-
#locked? ⇒ true, false
returns our current idea of whether or not we hold the lock, which does not actually check the state on the server.
- #unlock ⇒ true, false
-
#unlock! ⇒ true, false
deprecated
Deprecated.
the use of unlock! is deprecated and may be removed or have its semantics changed in a future release
-
#with_lock ⇒ Object
block caller until lock is aquired, then yield.
Methods included from ZK::Logging
Constructor Details
#initialize(client, name, root_lock_node = nil) ⇒ LockerBase
Create a new lock instance.
48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 |
# File 'lib/zk/locker/locker_base.rb', line 48 def initialize(client, name, root_lock_node=nil) @zk = client @root_lock_node = root_lock_node || Locker.default_root_lock_node @path = name @locked = false @waiting = false @lock_path = nil @parent_stat = nil @root_lock_path = "#{@root_lock_node}/#{@path.gsub("/", "__")}" @mutex = Monitor.new @cond = @mutex.new_cond @node_deletion_watcher = nil end |
Instance Attribute Details
#lock_path ⇒ String (readonly)
our absolute lock node path
24 25 26 |
# File 'lib/zk/locker/locker_base.rb', line 24 def lock_path @lock_path end |
Instance Method Details
#acquirable? ⇒ Boolean
It should be obvious, but there is no way to guarantee that between the time this method checks the server and taking any action to acquire the lock, another client may grab the lock before us (or converseley, another client may release the lock). This is simply meant as an advisory, and may be useful in some cases.
- If this instance holds the lock is true we return true (as we have already succeeded in acquiring the lock)
- If this instance doesn't hold the lock, we'll do a check on the server
to see if there are any participants who hold the lock and would
prevent us from acquiring the lock.
- If this instance could acquire the lock we will return true.
- If another client would prevent us from acquiring the lock, we return false.
118 119 120 |
# File 'lib/zk/locker/locker_base.rb', line 118 def acquirable? raise NotImplementedError end |
#assert! ⇒ Object
This is for users who wish to check that the assumption is correct that they actually still hold the lock. (check for session interruption, perhaps a lock is obtained in one method and handed to another)
This, unlike #locked? will actually go and check the conditions that constitute "holding the lock" with the server.
234 235 236 237 238 239 240 241 242 243 |
# File 'lib/zk/locker/locker_base.rb', line 234 def assert! @mutex.synchronize do raise LockAssertionFailedError, "have not obtained the lock yet" unless locked? raise LockAssertionFailedError, "not connected" unless zk.connected? raise LockAssertionFailedError, "lock_path was #{lock_path.inspect}" unless lock_path raise LockAssertionFailedError, "the lock path #{lock_path} did not exist!" unless zk.exists?(lock_path) raise LockAssertionFailedError, "the parent node was replaced!" unless root_lock_path_same? raise LockAssertionFailedError, "we do not actually hold the lock" unless got_lock? end end |
#lock(blocking = false) ⇒ true, ...
165 166 167 |
# File 'lib/zk/locker/locker_base.rb', line 165 def lock(blocking=false) raise NotImplementedError end |
#lock!(blocking = false) ⇒ true, ...
the use of lock! is deprecated and may be removed or have its semantics changed in a future release
172 173 174 |
# File 'lib/zk/locker/locker_base.rb', line 172 def lock!(blocking=false) lock(blocking) end |
#lock_basename ⇒ nil, String
the basename of our lock path
86 87 88 |
# File 'lib/zk/locker/locker_base.rb', line 86 def lock_basename synchronize { lock_path and File.basename(lock_path) } end |
#locked? ⇒ true, false
returns our current idea of whether or not we hold the lock, which does not actually check the state on the server.
The reason for the equivocation around thinking we hold the lock is to contrast our current state and the actual state on the server. If you want to make double-triple certain of the state of the lock, use #assert!
100 101 102 |
# File 'lib/zk/locker/locker_base.rb', line 100 def locked? synchronize { !!@locked } end |
#unlock ⇒ true, false
There is more than one way you might not "own the lock" see issue #34
130 131 132 133 134 135 136 137 138 139 140 141 142 |
# File 'lib/zk/locker/locker_base.rb', line 130 def unlock rval = false @mutex.synchronize do if @locked logger.debug { "unlocking" } rval = cleanup_lock_path! @locked = false @node_deletion_watcher = nil @cond.broadcast end end rval end |
#unlock! ⇒ true, false
the use of unlock! is deprecated and may be removed or have its semantics changed in a future release
There is more than one way you might not "own the lock" see issue #34
147 148 149 |
# File 'lib/zk/locker/locker_base.rb', line 147 def unlock! unlock end |
#with_lock ⇒ Object
block caller until lock is aquired, then yield
there is no non-blocking version of this method
68 69 70 71 72 73 |
# File 'lib/zk/locker/locker_base.rb', line 68 def with_lock lock(true) yield ensure unlock end |