Class: NRSER::Stash
Overview
Abstract generalization of ActiveSupport::HashWithIndifferentAccess. Extends Hash and provides simple hooks for handling keys and values on write.
The Stuff You Care About collapse
- #[]=(key, value) ⇒ Object (also: #store)
-
#convert_key(key) ⇒ *
Convert an external key to the internal representation.
- #convert_value(value, options = {}) ⇒ Object
- #put(key, value) ⇒ Object
Class Method Summary collapse
Instance Method Summary collapse
-
#[](key) ⇒ Object
Same as
Hash#[]
where the key passed as argument can be either a string or a symbol:. - #_raw_get ⇒ Object
- #compact ⇒ Object
-
#default(*args) ⇒ Object
Same as
Hash#default
where the key passed as argument can be either a string or a symbol:. -
#delete(key) ⇒ Object
Removes the specified key from the hash.
-
#dig(*args) ⇒ Object
Same as
Hash#dig
where the key passed as argument can be either a string or a symbol:. -
#dup ⇒ Object
Returns a shallow copy of the hash.
-
#extractable_options? ⇒ Boolean
Returns
true
so thatArray#extract_options!
finds members of this class. -
#fetch(key, *extras) ⇒ Object
Same as
Hash#fetch
where the key passed as argument can be either a string or a symbol:. -
#initialize(constructor = {}) ⇒ Stash
constructor
Construction ==========================================================================.
-
#key?(key) ⇒ Boolean
(also: #include?, #has_key?, #member?)
Checks the hash for a key matching the argument passed in:.
-
#merge(hash, &block) ⇒ Object
This method has the same semantics of
update
, except it does not modify the receiver but rather returns a new hash with indifferent access with the result of the merge. - #reject(*args, &block) ⇒ Object
-
#replace(other_hash) ⇒ Object
Replaces the contents of this hash with other_hash.
-
#reverse_merge(other_hash) ⇒ Object
Like
merge
but the other way around: Merges the receiver into the argument and returns a new hash with indifferent access as result:. -
#reverse_merge!(other_hash) ⇒ Object
Same semantics as
reverse_merge
but modifies the receiver in-place. -
#select(*args, &block) ⇒ Object
def stringify_keys!; self end def deep_stringify_keys!; self end def stringify_keys; dup end def deep_stringify_keys; dup end undef :symbolize_keys! undef :deep_symbolize_keys! def symbolize_keys; to_hash.symbolize_keys! end def deep_symbolize_keys; to_hash.deep_symbolize_keys! end def to_options!; self end.
- #set_defaults(target) ⇒ Object
-
#to_hash ⇒ Object
Convert to a regular hash with string keys.
- #transform_values(*args, &block) ⇒ Object
-
#update(other_hash, &block) ⇒ self
(also: #merge!)
Updates the receiver in-place, merging in the hash passed as argument:.
-
#values_at(*indices) ⇒ Object
Returns an array of the values at the specified indices:.
Methods inherited from Hash
#bury, #bury!, #extract_values_at!, #str_keys, #str_keys!, #sym_keys, #sym_keys!, #to_options, #to_options!, #to_pair, #transform_values_with_keys, #transform_values_with_keys!
Methods included from Ext::Tree
#each_branch, #leaves, #map_branches, #map_leaves, #map_tree
Constructor Details
#initialize(constructor = {}) ⇒ Stash
Construction
27 28 29 30 31 32 33 34 35 36 37 38 |
# File 'lib/nrser/labs/stash.rb', line 27 def initialize(constructor = {}) if constructor.respond_to?(:to_hash) super() update(constructor) hash = constructor.to_hash self.default = hash.default if hash.default self.default_proc = hash.default_proc if hash.default_proc else super(constructor) end end |
Class Method Details
Instance Method Details
#[](key) ⇒ Object
Same as Hash#[]
where the key passed as argument can be either a string or a symbol:
counters = ActiveSupport::HashWithIndifferentAccess.new
counters[:foo] = 1
counters['foo'] # => 1
counters[:foo] # => 1
counters[:zoo] # => nil
226 227 228 |
# File 'lib/nrser/labs/stash.rb', line 226 def [] key _raw_get convert_key( key ) end |
#[]=(key, value) ⇒ Object Also known as: store
124 125 126 |
# File 'lib/nrser/labs/stash.rb', line 124 def []= key, value put key, value end |
#_raw_get ⇒ Object
215 |
# File 'lib/nrser/labs/stash.rb', line 215 alias_method :_raw_get, :[] |
#compact ⇒ Object
357 358 359 |
# File 'lib/nrser/labs/stash.rb', line 357 def compact dup.tap(&:compact!) end |
#convert_key(key) ⇒ *
Convert an external key to the internal representation.
109 110 111 |
# File 'lib/nrser/labs/stash.rb', line 109 def convert_key key key end |
#convert_value(value, options = {}) ⇒ Object
114 115 116 |
# File 'lib/nrser/labs/stash.rb', line 114 def convert_value value, = {} value end |
#default(*args) ⇒ Object
Same as Hash#default
where the key passed as argument can be either a string or a symbol:
hash = ActiveSupport::HashWithIndifferentAccess.new(1)
hash.default # => 1
hash = ActiveSupport::HashWithIndifferentAccess.new { |hash, key| key }
hash.default # => nil
hash.default('foo') # => 'foo'
hash.default(:foo) # => 'foo'
269 270 271 |
# File 'lib/nrser/labs/stash.rb', line 269 def default(*args) super(*args.map { |arg| convert_key(arg) }) end |
#delete(key) ⇒ Object
Removes the specified key from the hash.
328 329 330 |
# File 'lib/nrser/labs/stash.rb', line 328 def delete(key) super(convert_key(key)) end |
#dig(*args) ⇒ Object
Same as Hash#dig
where the key passed as argument can be either a string or a symbol:
counters = ActiveSupport::HashWithIndifferentAccess.new
counters[:foo] = { bar: 1 }
counters.dig('foo', 'bar') # => 1
counters.dig(:foo, :bar) # => 1
counters.dig(:zoo) # => nil
253 254 255 256 |
# File 'lib/nrser/labs/stash.rb', line 253 def dig *args args[0] = convert_key( args[0] ) if args.size > 0 super *args end |
#dup ⇒ Object
Returns a shallow copy of the hash.
hash = ActiveSupport::HashWithIndifferentAccess.new({ a: { b: 'b' } })
dup = hash.dup
dup[:a][:c] = 'c'
hash[:a][:c] # => "c"
dup[:a][:c] # => "c"
291 292 293 294 295 |
# File 'lib/nrser/labs/stash.rb', line 291 def dup self.class.new(self).tap do |new_hash| set_defaults(new_hash) end end |
#extractable_options? ⇒ Boolean
Returns true
so that Array#extract_options!
finds members of this class.
145 146 147 |
# File 'lib/nrser/labs/stash.rb', line 145 def true end |
#fetch(key, *extras) ⇒ Object
Same as Hash#fetch
where the key passed as argument can be either a string or a symbol:
counters = ActiveSupport::HashWithIndifferentAccess.new
counters[:foo] = 1
counters.fetch('foo') # => 1
counters.fetch(:bar, 0) # => 0
counters.fetch(:bar) { |key| 0 } # => 0
counters.fetch(:zoo) # => KeyError: key not found: "zoo"
240 241 242 |
# File 'lib/nrser/labs/stash.rb', line 240 def fetch key, *extras super convert_key(key), *extras end |
#key?(key) ⇒ Boolean Also known as: include?, has_key?, member?
Checks the hash for a key matching the argument passed in:
hash = ActiveSupport::HashWithIndifferentAccess.new
hash['key'] = 'value'
hash.key?(:key) # => true
hash.key?('key') # => true
206 207 208 |
# File 'lib/nrser/labs/stash.rb', line 206 def key? key _raw_key? convert_key( key ) end |
#merge(hash, &block) ⇒ Object
This method has the same semantics of update
, except it does not modify the receiver but rather returns a new hash with indifferent access with the result of the merge.
300 301 302 |
# File 'lib/nrser/labs/stash.rb', line 300 def merge(hash, &block) dup.update(hash, &block) end |
#put(key, value) ⇒ Object
119 120 121 |
# File 'lib/nrser/labs/stash.rb', line 119 def put key, value _convert_and_put key, value end |
#reject(*args, &block) ⇒ Object
347 348 349 350 |
# File 'lib/nrser/labs/stash.rb', line 347 def reject(*args, &block) return to_enum(:reject) unless block_given? dup.tap { |hash| hash.reject!(*args, &block) } end |
#replace(other_hash) ⇒ Object
Replaces the contents of this hash with other_hash.
h = { "a" => 100, "b" => 200 }
h.replace({ "c" => 300, "d" => 400 }) # => {"c"=>300, "d"=>400}
323 324 325 |
# File 'lib/nrser/labs/stash.rb', line 323 def replace(other_hash) super(self.class.new(other_hash)) end |
#reverse_merge(other_hash) ⇒ Object
Like merge
but the other way around: Merges the receiver into the argument and returns a new hash with indifferent access as result:
hash = ActiveSupport::HashWithIndifferentAccess.new
hash['a'] = nil
hash.reverse_merge(a: 0, b: 1) # => {"a"=>nil, "b"=>1}
310 311 312 |
# File 'lib/nrser/labs/stash.rb', line 310 def reverse_merge(other_hash) super(self.class.new(other_hash)) end |
#reverse_merge!(other_hash) ⇒ Object
Same semantics as reverse_merge
but modifies the receiver in-place.
315 316 317 |
# File 'lib/nrser/labs/stash.rb', line 315 def reverse_merge!(other_hash) replace(reverse_merge(other_hash)) end |
#select(*args, &block) ⇒ Object
def stringify_keys!; self end def deep_stringify_keys!; self end def stringify_keys; dup end def deep_stringify_keys; dup end undef :symbolize_keys! undef :deep_symbolize_keys! def symbolize_keys; to_hash.symbolize_keys! end def deep_symbolize_keys; to_hash.deep_symbolize_keys! end def to_options!; self end
342 343 344 345 |
# File 'lib/nrser/labs/stash.rb', line 342 def select(*args, &block) return to_enum(:select) unless block_given? dup.tap { |hash| hash.select!(*args, &block) } end |
#set_defaults(target) ⇒ Object
134 135 136 137 138 139 140 |
# File 'lib/nrser/labs/stash.rb', line 134 def set_defaults(target) if default_proc target.default_proc = default_proc.dup else target.default = default end end |
#to_hash ⇒ Object
Convert to a regular hash with string keys.
362 363 364 365 366 367 368 369 370 |
# File 'lib/nrser/labs/stash.rb', line 362 def to_hash _new_hash = ::Hash.new set_defaults(_new_hash) each do |key, value| _new_hash[key] = convert_value(value, for: :to_hash) end _new_hash end |
#transform_values(*args, &block) ⇒ Object
352 353 354 355 |
# File 'lib/nrser/labs/stash.rb', line 352 def transform_values(*args, &block) return to_enum(:transform_values) unless block_given? dup.tap { |hash| hash.transform_values!(*args, &block) } end |
#update(other_hash, &block) ⇒ self Also known as: merge!
Updates the receiver in-place, merging in the hash passed as argument:
hash_1 = ActiveSupport::HashWithIndifferentAccess.new
hash_1[:key] = 'value'
hash_2 = ActiveSupport::HashWithIndifferentAccess.new
hash_2[:key] = 'New Value!'
hash_1.update(hash_2) # => {"key"=>"New Value!"}
The argument can be either an ActiveSupport::HashWithIndifferentAccess
or a regular Hash
. In either case the merge respects the semantics of indifferent access.
If the argument is a regular hash with keys :key
and “key” only one of the values end up in the receiver, but which one is unspecified.
When given a block, the value for duplicated keys will be determined by the result of invoking the block with the duplicated key, the value in the receiver, and the value in other_hash
. The rules for duplicated keys follow the semantics of indifferent access:
hash_1[:key] = 10
hash_2['key'] = 12
hash_1.update(hash_2) { |key, old, new| old + new } # => {"key"=>22}
186 187 188 189 190 191 192 193 194 195 |
# File 'lib/nrser/labs/stash.rb', line 186 def update other_hash, &block other_hash.to_hash.each_pair do |key, value| key = convert_key key if block && _raw_key?( key ) value = yield key, _raw_get( key ), value end put key, value end self end |
#values_at(*indices) ⇒ Object
Returns an array of the values at the specified indices:
hash = ActiveSupport::HashWithIndifferentAccess.new
hash[:a] = 'x'
hash[:b] = 'y'
hash.values_at('a', 'b') # => ["x", "y"]
279 280 281 |
# File 'lib/nrser/labs/stash.rb', line 279 def values_at(*indices) indices.collect { |key| self[convert_key(key)] } end |