Module: Predicated::Selectable

Defined in:
lib/predicated/selectable.rb

Defined Under Namespace

Modules: ClassMethods

Constant Summary collapse

SELECTORS =
:@_predicated_selectors

Class Method Summary collapse

Instance Method Summary collapse

Class Method Details

.bless_enumerable(enumerable, selectors) ⇒ Object

Make an Enumerable instance into a Selectable. This does for instances what “include Selectable” does for classes. todo: rename?



17
18
19
20
21
22
# File 'lib/predicated/selectable.rb', line 17

def self.bless_enumerable(enumerable, selectors)
  enumerable.singleton_class.instance_eval do
    include Selectable
    selector selectors
  end
end

.included(base) ⇒ Object



37
38
39
# File 'lib/predicated/selectable.rb', line 37

def self.included(base)
  base.extend ClassMethods
end

.merge_many(*hashes) ⇒ Object

merge several hashes into one, skipping nils todo: unit test todo: move onto Hash?



27
28
29
30
31
32
33
# File 'lib/predicated/selectable.rb', line 27

def self.merge_many(*hashes)
  result = {}
  hashes.compact.each do |hash|
    result.merge! hash
  end
  result
end

Instance Method Details

#select(*keys, &block) ⇒ Object



54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
# File 'lib/predicated/selectable.rb', line 54

def select(*keys, &block)
  if block_given?
    super
  else
    key = keys.shift
    result =
      if key
        selecting_proc = selectors[key]
        raise "no selector found for '#{key}'.  current selectors: [#{selectors.collect { |k, v| k.to_s }.join(",")}]" unless selecting_proc
        memos_for(:select)[key] ||= begin
          super(&selecting_proc)
        end
      else
        raise "select must be called with either a key or a block"
      end

    Selectable.bless_enumerable(result, selectors)

    if keys.length >= 1
      result.select(*keys, &block)
    else
      result
    end
  end
end

#selectorsObject



47
48
49
50
51
52
# File 'lib/predicated/selectable.rb', line 47

def selectors
  class_selectors = self.class.instance_variable_get(SELECTORS)
  singleton_selectors = self.singleton_class.instance_variable_get(SELECTORS)
  instance_selectors = self.instance_variable_get(SELECTORS)
  Selectable.merge_many(class_selectors, singleton_selectors, instance_selectors)
end