Skip to content
Browse files

Fix serializable_hash with xml generation and default :except option

When generating xml with a custom implementation of serializable_hash,
if using the :except option, it was being overriden by the default AR
implementation that attempts to ignore the inheritance column from STI
automatically. So, if you have an implementation like this:

    def serializable_hash(options={})
      super({ except: %w(some_attr) }.merge!(options))
    end

The :except option was correctly being used for :json generation, but
not for :xml, because the options hash already contained the :except
key with the inheritance column, thus overriding the customization.

This commit fixes this problem by removing the :except logic from the
xml serializer, that happened before calling serializable_hash. Since
serializable_hash also does the same check for inheritance column, this
logic was duplicated in both places, thus it's safe to remove it from
xml serializer (see ActiveRecord::Serialization#serializable_hash).

This is an attempt to solve issue #2498, that claims for a
"Single transformation API for both xml and json representations".
  • Loading branch information...
1 parent 965b779 commit 8b173f3bc5484a33ab985fd1a556f1f744e82cd7 @carlosantoniodasilva carlosantoniodasilva committed Jun 22, 2012
View
5 activerecord/lib/active_record/serializers/xml_serializer.rb
@@ -177,11 +177,6 @@ def to_xml(options = {}, &block)
end
class XmlSerializer < ActiveModel::Serializers::Xml::Serializer #:nodoc:
- def initialize(*args)
- super
- options[:except] = Array(options[:except]) | Array(@serializable.class.inheritance_column)
- end
-
class Attribute < ActiveModel::Serializers::Xml::Serializer::Attribute #:nodoc:
def compute_type
klass = @serializable.class
View
15 activerecord/test/cases/json_serialization_test.rb
@@ -115,6 +115,21 @@ def test_does_not_include_inheritance_column_from_sti
assert_no_match %r{ContactSti}, json
end
+ def test_serializable_hash_with_default_except_option_and_excluding_inheritance_column_from_sti
+ @contact = ContactSti.new(@contact.attributes)
+ assert_equal 'ContactSti', @contact.type
+
+ def @contact.serializable_hash(options={})
+ super({ except: %w(age) }.merge!(options))
+ end
+
+ json = @contact.to_json
+ assert_match %r{"name":"Konata Izumi"}, json
+ assert_no_match %r{age}, json
+ assert_no_match %r{type}, json
+ assert_no_match %r{ContactSti}, json
+ end
+
def test_serializable_hash_should_not_modify_options_in_argument
options = { :only => :name }
@contact.serializable_hash(options)
View
15 activerecord/test/cases/xml_serialization_test.rb
@@ -142,6 +142,21 @@ def test_does_not_include_inheritance_column_from_sti
assert_no_match %r{<type}, xml
assert_no_match %r{ContactSti}, xml
end
+
+ def test_serializable_hash_with_default_except_option_and_excluding_inheritance_column_from_sti
+ @contact = ContactSti.new(@contact.attributes)
+ assert_equal 'ContactSti', @contact.type
+
+ def @contact.serializable_hash(options={})
+ super({ except: %w(age) }.merge!(options))
+ end
+
+ xml = @contact.to_xml
+ assert_match %r{<name>aaron stack</name>}, xml
+ assert_no_match %r{age}, xml
+ assert_no_match %r{<type}, xml
+ assert_no_match %r{ContactSti}, xml
+ end
end
class DefaultXmlSerializationTimezoneTest < ActiveRecord::TestCase

0 comments on commit 8b173f3

Please sign in to comment.
Something went wrong with that request. Please try again.