Skip to content

Commit

Permalink
Merge pull request criteo-forks#8 from Mwea/feature/acl_retry
Browse files Browse the repository at this point in the history
Merge Consul ACL Retry
  • Loading branch information
kamaradclimber authored May 2, 2018
2 parents 2e0ab79 + 3fe5eee commit 47c1b13
Show file tree
Hide file tree
Showing 4 changed files with 89 additions and 6 deletions.
1 change: 1 addition & 0 deletions .foodcritic
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
~FC019
~FC028
~FC044
~FC109
7 changes: 7 additions & 0 deletions Gemfile
Original file line number Diff line number Diff line change
Expand Up @@ -12,3 +12,10 @@ gem 'poise-boiler'
gem 'poise-service', '~> 1.0'
gem 'rb-readline'
gem 'stove'

group :development do
gem 'diplomat'
gem 'github_changelog_generator', require: false
gem 'stove', require: false
gem 'webmock', '~> 3.1'
end
37 changes: 31 additions & 6 deletions libraries/consul_acl.rb
Original file line number Diff line number Diff line change
Expand Up @@ -79,8 +79,8 @@ def configure_diplomat
begin
require 'diplomat'
rescue LoadError
raise RunTimeError, 'The diplomat gem is required; ' \
'include recipe[consul::client_gem] to install.'
raise 'The diplomat gem is required; ' \
'include recipe[consul::client_gem] to install.'
end
Diplomat.configure do |config|
config.url = new_resource.url
Expand All @@ -90,10 +90,35 @@ def configure_diplomat
end

def up_to_date?
old_acl = Diplomat::Acl.info(new_resource.to_acl['ID'], nil, :return)
return false if old_acl.nil? || old_acl.empty?
old_acl.first.select! { |k, _v| %w(ID Type Name Rules).include?(k) }
old_acl.first == new_resource.to_acl
retry_block(max_tries: 3, sleep: 0.5) do
old_acl = Diplomat::Acl.info(new_resource.to_acl['ID'], nil, :return)
return false if old_acl.nil? || old_acl.empty?
old_acl.first.select! { |k, _v| %w(ID Type Name Rules).include?(k) }
old_acl.first == new_resource.to_acl
end
end

def retry_block(opts = {}, &_block)
opts = {
max_tries: 3, # Number of tries
sleep: 0, # Seconds to sleep between tries
}.merge(opts)

try_count = 1

begin
return yield try_count
rescue Diplomat::UnknownStatus
try_count += 1

# If we've maxed out our attempts, raise the exception to the calling code
raise if try_count > opts[:max_tries]

# Sleep before the next retry if the option was given
sleep opts[:sleep]

retry
end
end
end
end
Expand Down
50 changes: 50 additions & 0 deletions test/spec/libraries/consul_acl_spec.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
require 'spec_helper'
require 'webmock/rspec'
require 'diplomat'
require_relative '../../../libraries/consul_acl'

describe ConsulCookbook::Resource::ConsulAcl do
step_into(:consul_acl)
let(:chefspec_options) { { platform: 'ubuntu', version: '14.04' } }

context 'when the Consul agent is not ready' do
let(:info_body) do
[
{
'CreateIndex' => 3,
'ModifyIndex' => 3,
'ID' => 'client_token',
'Name' => 'Client Token',
'Type' => 'client',
'Rules' => {
'service' => {
'' => {
'policy' => 'write',
},
},
},
},
]
end
before do
json = JSON.generate(info_body.first)
stub_request(:get, %r{/v1/acl/info/})
.to_return(body: 'No cluster leader', status: 500).then
.to_return(body: json, status: 200)
stub_request(:put, %r{/v1/acl/create})
.to_return(body: json, status: 200)
end

recipe do
consul_acl 'client_token' do
acl_name 'Client Token'
type 'client'
auth_token 'ABC123'
end
end

it do
expect { chef_run }.to_not raise_error
end
end
end

0 comments on commit 47c1b13

Please sign in to comment.