diff options
-rw-r--r-- | lib/hashie/extensions/strict_key_access.rb | 27 | ||||
-rw-r--r-- | spec/hashie/extensions/strict_key_access_spec.rb | 49 |
2 files changed, 45 insertions, 31 deletions
diff --git a/lib/hashie/extensions/strict_key_access.rb b/lib/hashie/extensions/strict_key_access.rb index 6972252..78f86f3 100644 --- a/lib/hashie/extensions/strict_key_access.rb +++ b/lib/hashie/extensions/strict_key_access.rb @@ -15,7 +15,7 @@ module Hashie # >> hash[:cow] # KeyError: key not found: :cow # - # NOTE: For googlers coming from Python to Ruby, this extension makes a Hash behave like a "Dictionary". + # NOTE: For googlers coming from Python to Ruby, this extension makes a Hash behave more like a "Dictionary". # module StrictKeyAccess class DefaultError < StandardError @@ -24,20 +24,23 @@ module Hashie end end - # NOTE: This extension would break the default behavior of Hash initialization: + # NOTE: Defaults don't make any sense with a StrictKeyAccess. + # NOTE: When key lookup fails a KeyError is raised. # - # >> a = StrictKeyAccessHash.new(a: :b) + # Normal: + # + # >> a = Hash.new(123) # => {} - # >> a[:a] - # KeyError: key not found: :a + # >> a["noes"] + # => 123 + # + # With StrictKeyAccess: + # + # >> a = StrictKeyAccessHash.new(123) + # => {} + # >> a["noes"] + # KeyError: key not found: "noes" # - # Includes the Hashie::Extensions::MergeInitializer extension to get around that problem. - # Also note that defaults still don't make any sense with a StrictKeyAccess. - def self.included(base) - # Can only include into classes with a hash initializer - base.send(:include, Hashie::Extensions::MergeInitializer) - end - def [](key) fetch(key) end diff --git a/spec/hashie/extensions/strict_key_access_spec.rb b/spec/hashie/extensions/strict_key_access_spec.rb index 2e47064..273cab8 100644 --- a/spec/hashie/extensions/strict_key_access_spec.rb +++ b/spec/hashie/extensions/strict_key_access_spec.rb @@ -7,6 +7,12 @@ describe Hashie::Extensions::StrictKeyAccess do shared_examples_for 'StrictKeyAccess with valid key' do |options = {}| before { pending_for(options[:pending]) } if options[:pending] + context 'set' do + let(:new_value) { 42 } + it('returns value') do + expect(instance.send(:[]=, valid_key, new_value)).to eq new_value + end + end context 'access' do it('returns value') do expect(instance[valid_key]).to eq valid_value @@ -34,7 +40,7 @@ describe Hashie::Extensions::StrictKeyAccess do end end end - shared_examples_for 'StrictKeyAccess with exploding defaults' do + shared_examples_for 'StrictKeyAccess raises KeyError instead of allowing defaults' do context '#default' do it 'raises an error' do expect { instance.default(invalid_key) }.to raise_error Hashie::Extensions::StrictKeyAccess::DefaultError, @@ -62,8 +68,8 @@ describe Hashie::Extensions::StrictKeyAccess do end let(:klass) { StrictKeyAccessHash } - let(:instance) { StrictKeyAccessHash.new(*args) } - let(:args) do + let(:instance) { StrictKeyAccessHash.new(*initialization_args) } + let(:initialization_args) do [ { valid_key => valid_value } ] @@ -74,26 +80,31 @@ describe Hashie::Extensions::StrictKeyAccess do let(:invalid_value) { 'death' } context '.new' do - it_behaves_like 'StrictKeyAccess with valid key' + context 'no defaults at initialization' do + let(:initialization_args) { [] } + before do + instance.merge!(valid_key => valid_value) + end + it_behaves_like 'StrictKeyAccess with valid key' + it_behaves_like 'StrictKeyAccess with invalid key' + it_behaves_like 'StrictKeyAccess raises KeyError instead of allowing defaults' + end + context 'with defaults at initialization' do + before do + instance.merge!(valid_key => valid_value) + end + it_behaves_like 'StrictKeyAccess with valid key' + it_behaves_like 'StrictKeyAccess with invalid key' + it_behaves_like 'StrictKeyAccess raises KeyError instead of allowing defaults' + end it_behaves_like 'StrictKeyAccess with invalid key' - it_behaves_like 'StrictKeyAccess with exploding defaults' + it_behaves_like 'StrictKeyAccess raises KeyError instead of allowing defaults' end - context '[]' do - let(:instance) { StrictKeyAccessHash[*args] } + context '.[]' do + let(:instance) { StrictKeyAccessHash[*initialization_args] } it_behaves_like 'StrictKeyAccess with valid key', pending: { engine: 'rbx' } it_behaves_like 'StrictKeyAccess with invalid key', pending: { engine: 'rbx' } - it_behaves_like 'StrictKeyAccess with exploding defaults' - end - - context 'with default' do - let(:args) do - [ - { valid_key => valid_value }, invalid_value - ] - end - it_behaves_like 'StrictKeyAccess with valid key' - it_behaves_like 'StrictKeyAccess with invalid key' - it_behaves_like 'StrictKeyAccess with exploding defaults' + it_behaves_like 'StrictKeyAccess raises KeyError instead of allowing defaults' end end |