As a contrived example, imagine a UserAccount class that has a AuthorizationConfirmation instance as an attribute.
class CreateModels < ActiveRecord::MigrationAs you can see in the above example, the UserAccount class has the attribute authorization_confirmation. The value stored in authorization_confirmation is expected to be an instance of the AuthorizationConfirmation class.
def self.up
create_table :user_accounts do |t|
t.column :authorization_confirmation, :string
end
end
def self.down
drop_table :user_accounts
end
end
class UserAccount < ActiveRecord::Base
serialize :authorization_confirmation, AuthorizationConfirmation
end
class AuthorizationConfirmation
attr_accessor :fingerprint, :key
end
A simple test proves the expected behavior.
require File.expand_path(File.dirname(__FILE__) + "/../test_helper")The test proves that the instance of AuthorizationConfirmation is saved and retrieved as expected.
class UserAccountTest < Test::Unit::TestCase
def test_authorization_confirmation_is_serialized_and_deserialized
account = UserAccount.new
account.authorization_confirmation = AuthorizationConfirmation.new
account.authorization_confirmation.fingerprint = "Xc1sseE"
account.authorization_confirmation.key = "gEteEQ"
account.save
retrieved = UserAccount.find account.id
assert_equal "Xc1sseE", retrieved.authorization_confirmation.fingerprint
assert_equal "gEteEQ", retrieved.authorization_confirmation.key
end
end
A quick peek in the database shows the instance as yaml.
id | authorization_confirmationNOTE: At the time of this writing any attribute that is serialized cannot be nil. Ticket 7293 should resolve this problem.
----+------+-------------------------------------------------------------------------------
6 | --- !ruby/object:AuthorizationConfirmation
fingerprint: Xc1sseE
key: gEteEQ
Wouldn't it be more useful to use an aggregate (composed_of) for your purpose? Serialized attributes can't be used in conditions, aggregates can.
ReplyDeleteMichael,
ReplyDeleteUntil this week I had never seen composed_of or serialize so I really didn't know which option would be better. The composed_of method is much better documented; however, the serialize method seemed better suited for my specific case based on it's simple implementation. Part of this decision was based on the fact that my aggregate objects are reference data provided by an external service and I never need to query based on the values.
Thanks for the tip, I may switch to composed_of in the future just to see how it works out.
YMMV but I find serialization a major slow-down. One of my biggest methods had a 50% slowdown just due to one serialization. YAML is probably the culprit: slow as sh*t.
ReplyDelete