record.to_xml(:methods => other_ids) yields incorrect representation
Reported by Joran | June 20th, 2008 @ 07:49 AM
In Rails 2.1, one would expect that rendering a record (eg. an invoice) as xml, and including a method such as other_ids (eg. item_ids, which yields an array) would result in:
<invoice>
...
<item-ids>
<item-id>1</item-id>
<item-id>2</item-id>
...
</item-ids>
</invoice>
What actually results however is:
<invoice>
...
<item-ids>12</item-ids>
</invoice>
In other words, the other_ids method which returns an array is reduced by to_xml to a string containing the concatenated ids. What's interesting is that to_json doesn't have a problem with any of this and gives [1,2] as would be expected.
Comments and changes to this ticket
-
Clemens July 10th, 2008 @ 02:07 PM
- → Tag changed from to 2.1 activerecord bug to_xml
I think that's by design. As far as I see it, Rails converts a few types into "special" types and handles everything else as a string:
# taken from ActiveSupport::CoreExtensions::Hash::Conversions XML_TYPE_NAMES = { "Symbol" => "symbol", "Fixnum" => "integer", "Bignum" => "integer", "BigDecimal" => "decimal", "Float" => "float", "Date" => "date", "DateTime" => "datetime", "Time" => "datetime", "TrueClass" => "boolean", "FalseClass" => "boolean" } unless defined?(XML_TYPE_NAMES)Everything that isn't in this hash will automatically be turned into a string. I guess you could just call serialize the method yourself (which is not very DRY). But I honestly don't know - I think I wouldn't expose associations like this but rather use the :include option.
Just my 2 cents, of course.
-
Clemens July 10th, 2008 @ 02:09 PM
Oops, didn't mean to change the tags - that just happened ... (but I guess it's right that way anyways)
-
Joran July 10th, 2008 @ 02:35 PM
Hi Clemens, thanks for the comment. When it comes to type conversion, Rails certainly uses this to elegant effect in the JSON class.
However, the problem is that this is not a design issue (as applied to type conversion or content types). It's a data issue.
In other words, JSON and XML are merely data formats. The data itself should not change. In this case it does.
Rails to_json gets it right (Ruby array -> Javascript array). Rails to_xml gets it wrong (Ruby array -> concatenated string). to_xml gets resource collection arrays right. I see no reason why it can't get this right.
But regardless, it's a problem because :methods => other_ids is in the Rails docs and is supposed to be able to handle this. And to prove the point, the newly revamped Rails 2.1 to_json (which added :include and :methods support as far as I know) can handle this.
So it's actually quite a discrepancy. To resolve it, we either need to force to_json to concatenate any :methods => other_ids arrays to strings as to_xml does (which would serve no utilitarian purpose). Or update to_xml to the level that to_json is at in this regard.
Re: using :include vs :methods, I do use :include in other resources, but not for many-to-many resources where it makes more sense to use id references, as these kinds of relationships can often be of a more categorical/static/lookup nature.
In any event, the nature of REST is atomicity (i.e. smaller, simpler, lighter, factorized resources that can be cached and combined more easily with others in different ways as opposed to large data clumps). :methods is far closer to this ideal than :include.
It's important we get this fixed.
Please Login or create a free account to add a new comment.
You can update this ticket by sending an email to from your email client. (help)
Create your profile
Help contribute to this project by taking a few moments to create your personal profile. Create your profile »
Source available from github
The Git repository resides at http://github.com/rails
Check out the current development trunk (Edge Rails) with:
git clone git://github.com/rails/rails.git
The latest development for the 1.2.x and 2.0.x releases are on the 1-2-stable and 2-0-stable branches.
Creating a bug report
When creating a bug report, be sure to include as much relevant information as possible. Post the code sample that causes the problem. Preferably, alter the unit tests and show through either changed or added tests how the expected behavior is not occuring.
Security vulnerabilities should be reported via an email to security@rubyonrails.org, do not use trac for reporting security vulnerabilities. All content in trac is publicly available as soon as it is posted.
Then don't get your hopes up. Unless you have a "Code Red, Mission Critical, The World is Coming to an End" kinda bug, you're creating this ticket in the hope that others with the same problem will be able to collaborate with you on solving it. Do not expect that the ticket automatically will see any activity or that others will jump to fix it. Creating a ticket like this is mostly to help yourself start on the path of fixing the problem and for others to sign on to with a "I'm having this problem too".
