Module: ChainMethods

Included in:
AnnotatedArray, IndiferentHash, NamedArray, Path, Resource, TSV
Defined in:
lib/rbbt/util/chain_methods.rb

Class Method Summary collapse

Class Method Details

.chain_methods_extended(base) ⇒ Object



6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
# File 'lib/rbbt/util/chain_methods.rb', line 6

def self.chain_methods_extended(base)
    if not base.respond_to? :chain_prefix
      metaclass = class << base
        attr_accessor :chain_prefix, :chained_methods

        def chained_methods
          @chained_methods ||= instance_methods.select{|method| method =~ /^#{chain_prefix}/}
        end
        self
      end

      metaclass.module_eval do
        def setup_chains(base)
          raise "No prefix specified for #{self.to_s}" if self.chain_prefix.nil? or (String === self.chain_prefix and self.chain_prefix.empty?)
          methods = self.chained_methods

          return if methods.empty?

          prefix = self.chain_prefix

          if not base.respond_to?(:processed_chains) or base.processed_chains.nil? or not base.processed_chains.include? prefix
            class << base
              attr_accessor :processed_chains 
            end if not base.respond_to? :processed_chains

            base.processed_chains = Set.new if base.processed_chains.nil?
            base.processed_chains << prefix

            class << base; self; end.module_eval do
              methods.each do |new_method|
                original = new_method.sub(prefix.to_s + '_', '')
                clean_method = prefix.to_s + '_clean_' + original

                original = "[]" if original == "get_brackets"
                original = "[]=" if original == "set_brackets"

                if base.respond_to? clean_method
                  raise "Method already defined: #{clean_method}. #{ prefix }"
                end

                begin
                  alias_method clean_method, original 
                rescue
                end

                alias_method original, new_method
              end
            end
          end
        end
      end

      if not metaclass.respond_to? :extended
        metaclass.module_eval do
          alias prev_chain_methods_extended extended if methods.include? "extended"

          def extended(base)
            if self.respond_to? :prev_chain_methods_extended 
              prev_chain_methods_extended(base)
            end
            setup_chains(base)
          end
        end
      end
  end

  base.chain_prefix = base.to_s.downcase.to_sym
end

.extended(base) ⇒ Object



75
76
77
# File 'lib/rbbt/util/chain_methods.rb', line 75

def self.extended(base)
  chain_methods_extended(base)
end