views:

145

answers:

1

I have an ActiveRecord class that uses acts_as_tree. I'm trying to update the to_xml method so that if a child record's to_xml is called it will return it's xml nested in the parent/ancestor xml to give the fully-qualified path to that resource. As an example I have Compiler which is a parent of Compiler/Version. Compiler should be rendered as xml:

While Compiler/Version should render as

I've tried to do this by passing around a fully_qualified flag, but it dies with 'Builder::XmlMarkup#to_ary should return Array'

def to_xml(options={}, &block) options[:fully_qualified] ||= true options[:indent] ||= 2 options[:builder] ||= Builder::XmlMarkup.new(:indent => options[:indent])

if options[:fully_qualified] and not parent.nil?

55: parent.to_xml(options) do |foo| relative_options = options.dup relative_options[:fully_qualfied] = false relative_options[:skip_instruct] = true relative_options.delete(:builder)

    foo << to_xml(relative_options)
  end
else
  xml = options[:builder]
  xml.instruct! unless options[:skip_instruct]

66: xml.parameter(:name => name, &block) end end

The method works fine for the case of Compiler, but fails for Compiler/Version:

/usr/lib/ruby/1.8/builder/xmlbase.rb:133:in method_missing' /usr/lib/ruby/1.8/builder/xmlbase.rb:133:incall' /usr/lib/ruby/1.8/builder/xmlbase.rb:133:in _nested_structures' /usr/lib/ruby/1.8/builder/xmlbase.rb:57:inmethod_missing' app/models/parameter.rb:66:in to_xml' app/models/parameter.rb:55:into_xml'

+1  A: 

It appears that you can't call to_xml on any singular-association. to_xml on parent and parameter (both has_one relationships) failed, but if I did the lookup with find_by_id it worked:

def to_xml(options={}, &block) my_options = options.dup my_options[:fully_qualified] = true unless my_options.has_key?(:fully_qualified) my_options[:only] = [:name]

if my_options[:fully_qualified] and not parent.nil?
   # do block here fails with 'Builder::XmlMarkup#to_ary should return Array'
   # if called as parent.to_xml, so call on explicit lookup of parent and
   # it works
   p = self.class.find_by_id(parent_id)
   p.to_xml(my_options) do |xml|
     relative_options = my_options.dup
     relative_options[:builder] = xml
     relative_options[:fully_qualified] = false
     relative_options[:skip_instruct] = true

     to_xml(relative_options, &block)
   end
else
  super(my_options, &block)
end

end

Luke Imhoff