redlock 0.1.1 → 0.1.2

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 CHANGED
@@ -1,15 +1,7 @@
1
1
  ---
2
- !binary "U0hBMQ==":
3
- metadata.gz: !binary |-
4
- N2ZjYTlmOTc2ZTc0MmYxZGE0MzBiNzY2ZjEzOGMxOWU4YjE3NzRhMQ==
5
- data.tar.gz: !binary |-
6
- NjMwOGMxNTRkMDliODFmYjI3YWY5MWQ3ZTdjMjUzMDNlNTdiNDQ4Yg==
2
+ SHA1:
3
+ metadata.gz: e2d0a189eba4a2f362d02f034cfa0957eba666eb
4
+ data.tar.gz: 18f9e90023c218eb9b5d65a71946b39fb98a8617
7
5
  SHA512:
8
- metadata.gz: !binary |-
9
- ZTg2ZTI4MzY0ZmI3MzhkYzlhNTA3NzVjMGYyZmJlNGVhNjAzODE0ZGY4M2Qz
10
- NDI2ODJmYzU5MGI2YjM3MmMxNGQwNTRlYzM4ZTE0MWNhNmQyYWVlNGUyYmU4
11
- YWM0OTUyMzQwNzdlNTk2ZTNiNGE4OTdjYTQzYmYwMjBjYjU5YmE=
12
- data.tar.gz: !binary |-
13
- N2Q1ZTcwZWRlNDYyZjY0MzY4MDA4ZTVhMjEwNTE3N2Q4MWZmOTY0MDA0MmIx
14
- MjVlYzM3ZWQ1Y2RkODJiOTI0ZTZiYWQ3MjdmZWU2NWZkNzMyMGM2YzM2OTUy
15
- NWJmMjNmNjU0YzgyNDNkNGVhMDM2OWJjZmMzY2NhMWY4MzVjZjI=
6
+ metadata.gz: 65cd0b7c60b9756eba2f0fcce27677b9f26e32db74f3cbea7f036744ae52bfd0e50f8ce72cddb538fafc49a409c0f7a6257976d9234be8305d8a77151958980d
7
+ data.tar.gz: 0531fe15435ad4601ad83c8aa107ac6e3073f4f2be49682c74ff379f9b9c20f603e140b51c604b5baffdfb7650a3e4762cdea9495870fa1b684f99bcbab6930d
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- redlock (0.1.0)
4
+ redlock (0.1.2)
5
5
  redis (~> 3, >= 3.0.5)
6
6
 
7
7
  GEM
data/README.md CHANGED
@@ -84,7 +84,7 @@ end
84
84
  Make sure you have at least 1 redis instances up.
85
85
 
86
86
  $ rspec
87
-
87
+
88
88
  ## Disclaimer
89
89
 
90
90
  This code implements an algorithm which is currently a proposal, it was not formally analyzed. Make sure to understand how it works before using it in your production environments. You can see discussion about this approach at [reddit](http://www.reddit.com/r/programming/comments/2nt0nq/distributed_lock_using_redis_implemented_in_ruby/).
@@ -74,6 +74,8 @@ module Redlock
74
74
  else
75
75
  @redis = Redis.new(connection)
76
76
  end
77
+
78
+ load_scripts
77
79
  end
78
80
 
79
81
  def lock(resource, val, ttl)
@@ -81,10 +83,16 @@ module Redlock
81
83
  end
82
84
 
83
85
  def unlock(resource, val)
84
- @redis.eval(UNLOCK_SCRIPT, [resource], [val])
86
+ @redis.evalsha(@unlock_script_sha, keys: [resource], argv: [val])
85
87
  rescue
86
88
  # Nothing to do, unlocking is just a best-effort attempt.
87
89
  end
90
+
91
+ private
92
+
93
+ def load_scripts
94
+ @unlock_script_sha = @redis.script(:load, UNLOCK_SCRIPT)
95
+ end
88
96
  end
89
97
 
90
98
  def try_lock_instances(resource, ttl)
@@ -0,0 +1,37 @@
1
+ module Redlock
2
+ class Client
3
+ attr_writer :testing_mode
4
+
5
+ alias_method :try_lock_instances_without_testing, :try_lock_instances
6
+
7
+ def try_lock_instances(resource, ttl)
8
+ if @testing_mode == :bypass
9
+ {
10
+ validity: ttl,
11
+ resource: resource,
12
+ value: SecureRandom.uuid
13
+ }
14
+ elsif @testing_mode == :fail
15
+ false
16
+ else
17
+ try_lock_instances_without_testing resource, ttl
18
+ end
19
+ end
20
+
21
+ alias_method :unlock_without_testing, :unlock
22
+
23
+ def unlock(lock_info)
24
+ unlock_without_testing lock_info unless @testing_mode == :bypass
25
+ end
26
+
27
+ class RedisInstance
28
+ def load_scripts
29
+ begin
30
+ @unlock_script_sha = @redis.script(:load, UNLOCK_SCRIPT)
31
+ rescue Redis::CommandError
32
+ # ignore
33
+ end
34
+ end
35
+ end
36
+ end
37
+ end
@@ -1,3 +1,3 @@
1
1
  module Redlock
2
- VERSION = "0.1.1"
2
+ VERSION = "0.1.2"
3
3
  end
@@ -9,14 +9,14 @@ RSpec.describe Redlock::Client do
9
9
 
10
10
  describe 'initialize' do
11
11
  it 'accepts both redis URLs and Redis objects' do
12
- servers = [ 'redis://localhost:6379', Redis.new(url: 'redis://someotherhost:6379') ]
12
+ servers = [ 'redis://localhost:6379', Redis.new(url: 'redis://127.0.0.1:6379') ]
13
13
  redlock = Redlock::Client.new(servers)
14
14
 
15
15
  redlock_servers = redlock.instance_variable_get(:@servers).map do |s|
16
16
  s.instance_variable_get(:@redis).client.host
17
17
  end
18
18
 
19
- expect(redlock_servers).to match_array(%w{ localhost someotherhost })
19
+ expect(redlock_servers).to match_array(%w{ localhost 127.0.0.1 })
20
20
  end
21
21
  end
22
22
 
@@ -1,5 +1,4 @@
1
1
  # coding: utf-8
2
- # $LOAD_PATH.unshift File.expand_path('../../lib', __FILE__)
3
2
  require 'coveralls'
4
3
  Coveralls.wear!
5
4
  require 'redlock'
@@ -0,0 +1,45 @@
1
+ require 'spec_helper'
2
+ require 'securerandom'
3
+
4
+ require 'redlock/testing'
5
+
6
+ RSpec.describe Redlock::Client do
7
+ let(:lock_manager) { Redlock::Client.new }
8
+ let(:resource_key) { SecureRandom.hex(3) }
9
+ let(:ttl) { 1000 }
10
+
11
+ describe '(testing mode)' do
12
+ describe 'try_lock_instances' do
13
+ context 'when testing with bypass mode' do
14
+ before { lock_manager.testing_mode = :bypass }
15
+
16
+ it 'bypasses the redis servers' do
17
+ expect(lock_manager).to_not receive(:try_lock_instances_without_testing)
18
+ lock_manager.lock(resource_key, ttl) do |lock_info|
19
+ expect(lock_info).to be_lock_info_for(resource_key)
20
+ end
21
+ end
22
+ end
23
+
24
+ context 'when testing with fail mode' do
25
+ before { lock_manager.testing_mode = :fail }
26
+
27
+ it 'fails' do
28
+ expect(lock_manager).to_not receive(:try_lock_instances_without_testing)
29
+ lock_manager.lock(resource_key, ttl) do |lock_info|
30
+ expect(lock_info).to eql(false)
31
+ end
32
+ end
33
+ end
34
+
35
+ context 'when testing is disabled' do
36
+ before { lock_manager.testing_mode = nil }
37
+
38
+ it 'works as usual' do
39
+ expect(lock_manager).to receive(:try_lock_instances_without_testing)
40
+ lock_manager.lock(resource_key, ttl) { |lock_info| }
41
+ end
42
+ end
43
+ end
44
+ end
45
+ end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: redlock
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.1
4
+ version: 0.1.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - Leandro Moreira
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2015-04-21 00:00:00.000000000 Z
11
+ date: 2015-09-13 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: redis
@@ -17,7 +17,7 @@ dependencies:
17
17
  - - ~>
18
18
  - !ruby/object:Gem::Version
19
19
  version: '3'
20
- - - ! '>='
20
+ - - '>='
21
21
  - !ruby/object:Gem::Version
22
22
  version: 3.0.5
23
23
  type: :runtime
@@ -27,7 +27,7 @@ dependencies:
27
27
  - - ~>
28
28
  - !ruby/object:Gem::Version
29
29
  version: '3'
30
- - - ! '>='
30
+ - - '>='
31
31
  - !ruby/object:Gem::Version
32
32
  version: 3.0.5
33
33
  - !ruby/object:Gem::Dependency
@@ -48,14 +48,14 @@ dependencies:
48
48
  name: coveralls
49
49
  requirement: !ruby/object:Gem::Requirement
50
50
  requirements:
51
- - - ! '>='
51
+ - - '>='
52
52
  - !ruby/object:Gem::Version
53
53
  version: '0'
54
54
  type: :development
55
55
  prerelease: false
56
56
  version_requirements: !ruby/object:Gem::Requirement
57
57
  requirements:
58
- - - ! '>='
58
+ - - '>='
59
59
  - !ruby/object:Gem::Version
60
60
  version: '0'
61
61
  - !ruby/object:Gem::Dependency
@@ -104,10 +104,12 @@ files:
104
104
  - Rakefile
105
105
  - lib/redlock.rb
106
106
  - lib/redlock/client.rb
107
+ - lib/redlock/testing.rb
107
108
  - lib/redlock/version.rb
108
109
  - redlock.gemspec
109
110
  - spec/client_spec.rb
110
111
  - spec/spec_helper.rb
112
+ - spec/testing_spec.rb
111
113
  homepage: https://github.com/leandromoreira/redlock-rb
112
114
  licenses:
113
115
  - BSD-2-Clause
@@ -118,12 +120,12 @@ require_paths:
118
120
  - lib
119
121
  required_ruby_version: !ruby/object:Gem::Requirement
120
122
  requirements:
121
- - - ! '>='
123
+ - - '>='
122
124
  - !ruby/object:Gem::Version
123
125
  version: '0'
124
126
  required_rubygems_version: !ruby/object:Gem::Requirement
125
127
  requirements:
126
- - - ! '>='
128
+ - - '>='
127
129
  - !ruby/object:Gem::Version
128
130
  version: '0'
129
131
  requirements: []
@@ -135,3 +137,4 @@ summary: Distributed lock using Redis written in Ruby.
135
137
  test_files:
136
138
  - spec/client_spec.rb
137
139
  - spec/spec_helper.rb
140
+ - spec/testing_spec.rb