Allow nested association access (assocs separated by “.” or “__”), e.g.: proxy_service.asset__gui_folder__name Example:
Book.first.genre__name = 'Fantasy'
is the same as:
Book.first.genre = Genre.find_by_name('Fantasy')
The result - easier forms and grids that handle nested models: simply specify column/field name as “genre__name“.
# File lib/netzke/active_record/association_attributes.rb, line 20
20: def method_missing_with_basepack(method, *args, &block)
21: # if refering to a column, just pass it to the original method_missing
22: return method_missing_without_basepack(method, *args, &block) if self.class.column_names.include?(method.to_s)
23:
24: split = method.to_s.split(/\.|__/)
25: if split.size > 1
26: if split.last =~ /=$/
27: if split.size == 2
28: # search for association and assign it to self
29: assoc = self.class.reflect_on_association(split.first.to_sym)
30: assoc_method = split.last.chop
31: if assoc
32: begin
33: assoc_instance = assoc.klass.send("find_by_#{assoc_method}", *args)
34: rescue NoMethodError
35: assoc_instance = nil
36: logger.debug "!!! no find_by_#{assoc_method} method for class #{assoc.klass.name}\n"
37: end
38: if (assoc_instance)
39: self.send("#{split.first}=", assoc_instance)
40: else
41: logger.debug "!!! Couldn't find association #{split.first} by #{assoc_method} '#{args.first}'"
42: end
43: else
44: method_missing_without_basepack(method, *args, &block)
45: end
46: else
47: method_missing_without_basepack(method, *args, &block)
48: end
49: else
50: res = self
51: split.each do |m|
52: if res.respond_to?(m)
53: res = res.send(m) unless res.nil?
54: else
55: res.nil? ? nil : method_missing_without_basepack(method, *args, &block)
56: end
57: end
58: res
59: end
60: else
61: method_missing_without_basepack(method, *args, &block)
62: end
63: end
Make respond_to? return true for association assignment method, like “genre__name=“
# File lib/netzke/active_record/association_attributes.rb, line 66
66: def respond_to_with_basepack?(method, include_private = false)
67: split = method.to_s.split(/__/)
68: if split.size > 1
69: if split.last =~ /=$/
70: if split.size == 2
71: # search for association and assign it to self
72: assoc = self.class.reflect_on_association(split.first.to_sym)
73: assoc_method = split.last.chop
74: if assoc
75: assoc.klass.respond_to?("find_by_#{assoc_method}")
76: else
77: respond_to_without_basepack?(method, include_private)
78: end
79: else
80: respond_to_without_basepack?(method, include_private)
81: end
82: else
83: # self.respond_to?(split.first) ? self.send(split.first).respond_to?(split[1..-1].join("__")) : false
84: respond_to_without_basepack?(method, include_private)
85: end
86: else
87: respond_to_without_basepack?(method, include_private)
88: end
89: end
Disabled; run with --debug to generate this.
Generated with the Darkfish Rdoc Generator 1.1.6.