Module: ActiveRecord::AttributeMethods::Serialization::ClassMethods
- Defined in:
- lib/active_record/attribute_methods/serialization.rb
Instance Method Summary collapse
-
#serialize(attr_name, class_name_or_coder = Object, **options) ⇒ Object
If you have an attribute that needs to be saved to the database as a serialized object, and retrieved by deserializing into the same object, then specify the name of that attribute using this method and serialization will be handled automatically.
Instance Method Details
#serialize(attr_name, class_name_or_coder = Object, **options) ⇒ Object
If you have an attribute that needs to be saved to the database as a serialized object, and retrieved by deserializing into the same object, then specify the name of that attribute using this method and serialization will be handled automatically.
The serialization format may be YAML, JSON, or any custom format using a custom coder class.
Keep in mind that database adapters handle certain serialization tasks for you. For instance: json
and jsonb
types in PostgreSQL will be converted between JSON object/array syntax and Ruby Hash
or Array
objects transparently. There is no need to use #serialize in this case.
For more complex cases, such as conversion to or from your application domain objects, consider using the ActiveRecord::Attributes API.
Parameters
-
attr_name
- The name of the attribute to serialize. -
class_name_or_coder
- Optional. May be one of the following:-
default - The attribute value will be serialized as YAML. The attribute value must respond to
to_yaml
. -
Array
- The attribute value will be serialized as YAML, but an emptyArray
will be serialized asNULL
. The attribute value must be anArray
. -
Hash
- The attribute value will be serialized as YAML, but an emptyHash
will be serialized asNULL
. The attribute value must be aHash
. -
JSON
- The attribute value will be serialized as JSON. The attribute value must respond toto_json
. -
custom coder - The attribute value will be serialized using the coder’s
dump(value)
method, and will be deserialized using the coder’sload(string)
method. Thedump
method may returnnil
to serialize the value asNULL
.
-
Options
-
:default
- The default value to use when no value is provided. If this option is not passed, the previous default value (if any) will be used. Otherwise, the default will benil
.
Examples
Serialize the preferences
attribute using YAML
class User < ActiveRecord::Base
serialize :preferences
end
Serialize the preferences
attribute using JSON
class User < ActiveRecord::Base
serialize :preferences, JSON
end
Serialize the preferences
Hash
using YAML
class User < ActiveRecord::Base
serialize :preferences, Hash
end
Serialize the preferences
attribute using a custom coder
class Rot13JSON
def self.rot13(string)
string.tr("a-zA-Z", "n-za-mN-ZA-M")
end
# Serializes an attribute value to a string that will be stored in the database.
def self.dump(value)
rot13(ActiveSupport::JSON.dump(value))
end
# Deserializes a string from the database to an attribute value.
def self.load(string)
ActiveSupport::JSON.load(rot13(string))
end
end
class User < ActiveRecord::Base
serialize :preferences, Rot13JSON
end
103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 |
# File 'lib/active_record/attribute_methods/serialization.rb', line 103 def serialize(attr_name, class_name_or_coder = Object, **) # When ::JSON is used, force it to go through the Active Support JSON encoder # to ensure special objects (e.g. Active Record models) are dumped correctly # using the #as_json hook. coder = if class_name_or_coder == ::JSON Coders::JSON elsif [:load, :dump].all? { |x| class_name_or_coder.respond_to?(x) } class_name_or_coder else Coders::YAMLColumn.new(attr_name, class_name_or_coder) end attribute(attr_name, **) do |cast_type| if type_incompatible_with_serialize?(cast_type, class_name_or_coder) raise ColumnNotSerializableError.new(attr_name, cast_type) end cast_type = cast_type.subtype if Type::Serialized === cast_type Type::Serialized.new(cast_type, coder) end end |