Module: DrNicMagicModels::MagicModel::InstanceMethods

Defined in:
lib/dr_nic_magic_models/magic_model.rb

Instance Method Summary collapse

Dynamic Method Handling

This class handles dynamic methods through the method_missing method

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



25
26
27
28
29
30
31
32
33
34
35
36
37
38
# File 'lib/dr_nic_magic_models/magic_model.rb', line 25

def method_missing(method, *args, &block)
  begin
    super 
  rescue
    if unknown_method? method
      result = find_belongs_to method, *args, &block 
      result = find_has_some method, *args, &block if not result
      result = find_has_some_indirect method, *args, &block if not result
      return result if result
    end
    add_known_unknown method
    raise
  end
end

Instance Method Details

#add_belongs_to(method, method_clean, options, *args, &block) ⇒ Object



69
70
71
72
# File 'lib/dr_nic_magic_models/magic_model.rb', line 69

def add_belongs_to(method, method_clean, options, *args, &block)
  self.class.send 'belongs_to', method_clean.to_sym, options rescue puts $!
  self.send(method, *args, &block)
end

#add_has_some(method, method_clean, options, *args, &block) ⇒ Object



103
104
105
106
107
# File 'lib/dr_nic_magic_models/magic_model.rb', line 103

def add_has_some(method, method_clean, options, *args, &block)
  association = method_clean.singularize == method_clean ? 'has_one' : 'has_many'
  self.class.send association, method_clean.to_sym, options rescue puts $!
  self.send(method, *args, &block)
end

#add_has_some_through(join_table, method, *args, &block) ⇒ Object



122
123
124
125
# File 'lib/dr_nic_magic_models/magic_model.rb', line 122

def add_has_some_through(join_table, method, *args, &block)
  self.class.send 'has_many', method, :through => join_table.to_sym
  self.send(method, *args, &block)
end

#add_known_unknown(method) ⇒ Object



40
41
42
43
# File 'lib/dr_nic_magic_models/magic_model.rb', line 40

def add_known_unknown(method)
  @known_unknowns ||= {}
  @known_unknowns[method] = true
end

#find_belongs_to(method, *args, &block) ⇒ Object



49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
# File 'lib/dr_nic_magic_models/magic_model.rb', line 49

def find_belongs_to(method, *args, &block)
  method_clean = clean_method method
  fkc = 
    begin
      self.class.connection.foreign_key_constraints(self.class.table_name, method_clean) 
    rescue NotImplementedError 
      nil
    end
  if !fkc.nil? && fkc.length > 0
    foreign_key = fkc.first.foreign_key
    options = {:dependent => :destroy, 
      :foreign_key => fkc.first.foreign_key, 
      :class_name => self.class.class_name(fkc.first.reference_table)}
  else
    foreign_key = self.class.columns.select {|column| column.name == method_clean.to_s.foreign_key}.first
  end
  options ||= {}
  return add_belongs_to(method, method_clean, options, *args, &block) if foreign_key
end

#find_has_some(method, *args, &block) ⇒ Object



74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
# File 'lib/dr_nic_magic_models/magic_model.rb', line 74

def find_has_some(method, *args, &block)
  method_clean = clean_method method
  fkc = [method_clean.to_s.pluralize, method_clean.to_s.singularize].inject({}) do |pair, table_name|
    fkc = begin
            self.class.connection.foreign_key_constraints(table_name)
          rescue NotImplementedError
            nil
          end
    pair[table_name] = fkc if not fkc.blank?
    pair
  end
  if not fkc.blank?
    # assumes there is only one table found - that schema doesn't have a singular and plural table of same name
    foreign_key = fkc.values.first.find {|fk| fk.reference_table == self.class.table_name}
    if foreign_key
      foreign_key = foreign_key.foreign_key
      table_name = fkc.keys.first
      klass = Module.const_get table_name.singularize.camelize rescue nil
      options = {:foreign_key => foreign_key, :class_name => klass.name}
    end
  end
  unless foreign_key
    klass = Module.const_get method_clean.to_s.downcase.singularize.camelize rescue nil
    foreign_key = klass.columns.select {|column| column.name == self.class.name.foreign_key}.first if klass
  end
  options ||= {}
  return add_has_some(method, method_clean, options, *args, &block) if foreign_key
end

#find_has_some_indirect(method, *args, &block) ⇒ Object



109
110
111
112
113
114
115
116
117
118
119
120
# File 'lib/dr_nic_magic_models/magic_model.rb', line 109

def find_has_some_indirect(method, *args, &block)
  klass = Module.const_get method.to_s.downcase.singularize.camelize rescue return
  join_table = nil
  self.connection.tables.each do |table|
    unless [self.class.table_name, klass.table_name].include? table
      columns = self.connection.columns(table).map(&:name)
      join_table = table if columns.include?(self.class.to_s.foreign_key) and columns.include?(klass.to_s.foreign_key) 
    end
    break if join_table
  end
  return add_has_some_through(join_table, method, *args, &block) if join_table
end

#unknown_method?(method) ⇒ Boolean

Returns:

  • (Boolean)


45
46
47
# File 'lib/dr_nic_magic_models/magic_model.rb', line 45

def unknown_method?(method)
  @known_unknowns.nil? or @known_unknowns.include? method
end