Module: Eyeballer::ClassMethods

Defined in:
lib/eyeballer.rb

Instance Method Summary collapse

Instance Method Details

#observe(name, actions = {}) ⇒ Object



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
# File 'lib/eyeballer.rb', line 9

def observe(name, actions = {})

  observer_klass = self
  class_name =  ::Extlib::Inflection.camelize(name)
  klass = ::Extlib::Inflection.constantize(class_name)

  klass.class_eval do

    cattr_accessor :eyeballed_methods
    self.eyeballed_methods||= {}
    self.eyeballed_methods.merge!(actions) {|key, oldval, newval| (Array(oldval).flatten << newval).uniq}

    unless method_defined? :eyeball_executer
      define_method :eyeball_executer do |name|
        observer_klass_instance = observer_klass.new
        Array(self.class.eyeballed_methods[name]).each do |hook|
          if observer_klass_instance.method(hook).arity > 0
            observer_klass_instance.send(hook, self)
          else
            observer_klass_instance.send(hook)
          end
        end
      end
    end

    self.eyeballed_methods.keys.each do |method_name|
      # Pinched from alias_method_chain:
      method_name_without_punctuation, punctuation = method_name.to_s.sub(/([?!=])$/, ''), $1
      aliased_name = "#{method_name_without_punctuation}_without_eyeball#{punctuation}"
      unless method_defined? aliased_name
        alias_method aliased_name, method_name
        define_method method_name do |*args|
          result = self.send(aliased_name, *args)
          eyeball_executer(method_name)
          result
        end
      end
    end

  end
end