Method: Simple::SQL::Connection#lock!
- Defined in:
- lib/simple/sql/connection/lock.rb
#lock!(key, key2 = nil, timeout: nil) ⇒ Object
Acquire an advisory lock.
This uses the pg_*_xact_lock locks - that once acquired, cannot be released, but will release automatically once the transaction ends. This is safer than the pg_advisory_lock group of functions.
For ease of use the key argument can also be a string - in which case we use a hash function to derive a key value. Usage example:
Simple::SQL.lock! "products", 12
Simple::SQL.ask "UPDATE products SET ... WHERE id=12"
Note that passing in a timeout value sets timeouts for all lock! invocations in this transaction.
41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 |
# File 'lib/simple/sql/connection/lock.rb', line 41 def lock!(key, key2 = nil, timeout: nil) unless in_transaction? raise "You cannot use lock! outside of a transaction" end if key.is_a?(String) # calculate a 31 bit checksum < 0 key = Digest::CRC32.hexdigest(key).to_i(16) # get a 32-bit stable checksum key &= ~0x80000000 # reset bit 31 key = -key # make it negative end # shorten key, key2 to the allowed number of bits if key2 key = apply_bitmask(key, MASK_31_BITS) key2 = apply_bitmask(key2, MASK_31_BITS) else key = apply_bitmask(key, MASK_63_BITS) end if timeout lock_w_timeout(key, key2, timeout) else lock_wo_timeout(key, key2) end end |