spec/client_spec.rb in redlock-2.0.1 vs spec/client_spec.rb in redlock-2.0.2
- old
+ new
@@ -74,10 +74,42 @@
describe 'lock' do
context 'when lock is available' do
after(:each) { lock_manager.unlock(@lock_info) if @lock_info }
+ context 'when redis connection error occurs' do
+ let(:servers_with_quorum) {
+ [
+ "redis://#{redis1_host}:#{redis1_port}",
+ "redis://#{redis2_host}:#{redis2_port}",
+ unreachable_redis
+ ]
+ }
+
+ let(:servers_without_quorum) {
+ [
+ "redis://#{redis1_host}:#{redis1_port}",
+ unreachable_redis,
+ unreachable_redis
+ ]
+ }
+
+ it 'locks if majority of redis instances are available' do
+ redlock = Redlock::Client.new(servers_with_quorum)
+
+ expect(redlock.lock(resource_key, ttl)).to be_truthy
+ end
+
+ it 'fails to acquire a lock if majority of Redis instances are not available' do
+ redlock = Redlock::Client.new(servers_without_quorum)
+
+ expect {
+ redlock.lock(resource_key, ttl)
+ }.to raise_error(Redlock::LockAcquisitionError)
+ end
+ end
+
it 'locks' do
@lock_info = lock_manager.lock(resource_key, ttl)
expect(resource_key).to_not be_lockable(lock_manager, ttl)
end
@@ -264,11 +296,14 @@
redis_instance = lock_manager.instance_variable_get(:@servers).first
redis_instance.instance_variable_set(:@redis, unreachable_redis)
expect {
lock_manager.lock(resource_key, ttl)
- }.to raise_error(RedisClient::CannotConnectError)
+ }.to raise_error(Redlock::LockAcquisitionError) do |e|
+ expect(e.errors[0]).to be_a(RedisClient::CannotConnectError)
+ expect(e.errors.count).to eq 1
+ end
end
end
context 'when a server comes back' do
it 'recovers from connection issues' do
@@ -276,11 +311,14 @@
redis_instance = lock_manager.instance_variable_get(:@servers).first
old_redis = redis_instance.instance_variable_get(:@redis)
redis_instance.instance_variable_set(:@redis, unreachable_redis)
expect {
lock_manager.lock(resource_key, ttl)
- }.to raise_error(RedisClient::CannotConnectError)
+ }.to raise_error(Redlock::LockAcquisitionError) do |e|
+ expect(e.errors[0]).to be_a(RedisClient::CannotConnectError)
+ expect(e.errors.count).to eq 1
+ end
redis_instance.instance_variable_set(:@redis, old_redis)
expect(lock_manager.lock(resource_key, ttl)).to be_truthy
end
end
@@ -306,14 +344,18 @@
context 'when the script re-loading fails' do
it 'does not try to to load the scripts to cache again twice' do
# This time we do not pass it through to Redis, in order to simulate a passing
# call to LOAD SCRIPT followed by another NOSCRIPT error. Imagine someone
# repeatedly calling SCRIPT FLUSH on our Redis instance.
- expect(@manipulated_instance).to receive(:load_scripts)
+ expect(@manipulated_instance).to receive(:load_scripts).exactly(8).times
expect {
lock_manager.lock(resource_key, ttl)
- }.to raise_error(/NOSCRIPT/)
+ }.to raise_error(Redlock::LockAcquisitionError) do |e|
+ expect(e.errors[0]).to be_a(RedisClient::CommandError)
+ expect(e.errors[0].message).to match(/NOSCRIPT/)
+ expect(e.errors.count).to eq 1
+ end
end
end
context 'when the script re-loading succeeds' do
it 'locks' do