Class: Hashr

Inherits:
Hash show all
Defined in:
lib/hashr.rb,
lib/hashr/version.rb,
lib/hashr/env_defaults.rb

Defined Under Namespace

Modules: EnvDefaults

Constant Summary collapse

TEMPLATE =
new
VERSION =
'0.0.21'

Class Attribute Summary collapse

Class Method Summary collapse

Instance Method Summary collapse

Methods inherited from Hash

#deep_merge, #deep_symbolize_keys, #deep_symbolize_keys!, #except, #slice

Constructor Details

#initialize(data = {}, definition = self.class.definition, &block) ⇒ Hashr

Returns a new instance of Hashr.



40
41
42
43
44
# File 'lib/hashr.rb', line 40

def initialize(data = {}, definition = self.class.definition, &block)
  replace((deep_hashrize(definition.deep_merge((data || {}).deep_symbolize_keys))))
  deep_defaultize(self)
  (class << self; self; end).class_eval(&block) if block_given?
end

Dynamic Method Handling

This class handles dynamic methods through the method_missing method

#method_missing(name, *args, &block) ⇒ Object



64
65
66
67
68
69
70
71
72
73
74
# File 'lib/hashr.rb', line 64

def method_missing(name, *args, &block)
  case name.to_s[-1, 1]
  when '?'
    !!self[name.to_s[0..-2].to_sym]
  when '='
    self[name.to_s[0..-2].to_sym] = args.first
  else
    raise(IndexError.new("Key #{name.inspect} is not defined.")) if !key?(name) && self.class.raise_missing_keys
    self[name]
  end
end

Class Attribute Details

.raise_missing_keysObject

Returns the value of attribute raise_missing_keys.



9
10
11
# File 'lib/hashr.rb', line 9

def raise_missing_keys
  @raise_missing_keys
end

Class Method Details

.deep_accessorize(hash) ⇒ Object



27
28
29
30
31
32
33
34
35
# File 'lib/hashr.rb', line 27

def deep_accessorize(hash)
  hash.each do |key, value|
    next unless value.is_a?(Hash)
    value[:_access] ||= []
    value[:_access] = Array(value[:_access])
    value.keys.each { |key| value[:_access] << key if value.respond_to?(key) }
    deep_accessorize(value)
  end
end

.default(defaults) ⇒ Object



19
20
21
# File 'lib/hashr.rb', line 19

def default(defaults)
  @defaults = deep_accessorize(defaults)
end

.defaultsObject



23
24
25
# File 'lib/hashr.rb', line 23

def defaults
  @defaults ||= {}
end

.define(definition) ⇒ Object



11
12
13
# File 'lib/hashr.rb', line 11

def define(definition)
  @definition = deep_accessorize(definition.deep_symbolize_keys)
end

.definitionObject



15
16
17
# File 'lib/hashr.rb', line 15

def definition
  @definition ||= {}
end

Instance Method Details

#[](key, default = nil) ⇒ Object



46
47
48
49
# File 'lib/hashr.rb', line 46

def [](key, default = nil)
  store(key.to_sym, Hashr.new(default)) if default && !key?(key)
  super(key.to_sym)
end

#[]=(key, value) ⇒ Object



51
52
53
# File 'lib/hashr.rb', line 51

def []=(key, value)
  super(key.to_sym, value.is_a?(Hash) ? self.class.new(value, {}) : value)
end

#include_accessors(accessors) ⇒ Object



80
81
82
# File 'lib/hashr.rb', line 80

def include_accessors(accessors)
  Array(accessors).each { |accessor| meta_class.send(:define_method, accessor) { self[accessor] } } if accessors
end

#include_modules(modules) ⇒ Object



76
77
78
# File 'lib/hashr.rb', line 76

def include_modules(modules)
  Array(modules).each { |mod| meta_class.send(:include, mod) } if modules
end

#meta_classObject



84
85
86
# File 'lib/hashr.rb', line 84

def meta_class
  class << self; self end
end

#respond_to?(name) ⇒ Boolean

Returns:

  • (Boolean)


60
61
62
# File 'lib/hashr.rb', line 60

def respond_to?(name)
  true
end

#set(path, value, stack = []) ⇒ Object



55
56
57
58
# File 'lib/hashr.rb', line 55

def set(path, value, stack = [])
  tokens = path.to_s.split('.')
  tokens.size == 1 ? self[path] = value : self[tokens.shift, Hashr.new].set(tokens.join('.'), value, stack)
end

#to_hashObject



88
89
90
91
92
93
# File 'lib/hashr.rb', line 88

def to_hash
  inject({}) do |hash, (key, value)|
    hash[key] = value.is_a?(Hashr) ? value.to_hash : value
    hash
  end
end