A mixin for making serializable objects
This npm provides a
Serializable mixin to streamline the process of writing
serializable classes. Include the mixin and implement two instance methods
::deserializeParams) to add serialization to your
Before digging into how to implement serializable classes, let's touch on how
to use them. To serialize an object, call
::serialize. To deserialize an
.deserialize on its class with the results of a previous call to
train1 = cars: 20hasCaboose: truetrain1State = train1serializetrain2 = Traindeserializetrain1Stateexpecttrain2carstoBe 20expecttrain2hasCaboosetoBe true
You can pass
.deserialize an optional second argument containing additional
non-serializable parameters which will be merged with the deserialized
parameters when constructing the object. For example, say that trains need a
reference to a
RailNetwork instance, but that the
serialized as part of
train1 = cars: 20hasCaboose: truerailNetwork: networktrain1State = train1serialize # does not contain a serialized RailNetworktrain2 = Traindeserializetrain1StaterailNetwork: network
Serializable mixin is implemented with the mixto
npm. To include it, use the
.includeInto class method or simply subclass
Serializable = require 'serializable'SerializableincludeIntothis
SerializableincludeIntothis:: -> @doors@engine
If all your parameters are scalars, this is all that's required. When deserializing, Serializable will match up the names of the keys in the params hash with the names of your constructor parameters to reconstruct your object.
auto1 = 2'v6'auto2 = Automobiledeserializeauto1serializeexpectauto2doorstoBe 2expectauto2enginetoBe 'v6'
You can also take a params hash as your constructor argument, in which case Serializable won't attempt to match up constructor parameter names.
SerializableincludeIntothis:: -> @cars@hasCaboose
If your params hash contains nested serialized objects, you'll need to
deserialize the nested objects before they are passed to the constructor of the
parent object. You perform this deserialization in the optional
::deserializeParams instance method.
:@pilot ?= name: "Bob"plane: this: -> @enginespilot: @pilotserialize:params.pilot = Pilotdeserializeparamspilotplane: thisparams
Using some JS trickery, this method is called before your object's constructor, allowing you to reference the instance being deserialized when deserializing its children. You can also perform pre-initialization in this method. Note that it is safe to modify the params object that is passed into your method. This is convenient when only a subset of your params need to be deserialized.
If you can't know the specific class of the object you are deserializing ahead
of time, you can call
::registerDeserializers on a superclass (or any
serializable class) to enable polymorphic deserialization.
VehicleregisterDeserializersPlaneTrainVehicleregisterDeserializerAutomobilevehicleStates = planetrainautomap vehicleserializevehicles = vehicleStatesmap VehicledeserializevehicleState