module RemiLib::RSConf::Serializable

Overview

The RemiLib::RSConf::Serializable module automatically generates methods for RSConf serialization when included.

Example

require "libremiliacr"

alias RSConf = RemiLib::RSConf

class Location
  include RSConf::Serializable

  @[RSConf::Field(key: "lat")]
  property latitude : Float64

  @[RSConf::Field(key: "long")]
  property longitude : Float64
end

class House
  include RSConf::Serializable
  property address : String
  property location : Location?
end

rsStr = %|
address = "Crystal Road 1234"
location = {
  lat: 12.3
  long: 34.5
}
|

parsed = RSConf::Parser.parse(rsStr)
house = House.fromRsconf(parsed)
house.address  # => "Crystal Road 1234"
house.location # => #<Location:0x10cd93d80 @latitude=12.3, @longitude=34.5>

Usage

Including RemiLib::RSConf::Serializable will create #toRsconf and self.fromRsconf methods on the current class, and a constructor which takes a RemiLib::RSConf::RSValue. By default, these methods serialize into an RSConf object containing the value of every instance variable, the keys being the instance variable name. Most primitives and collections supported as instance variable values (string, integer, array, hash, etc.), along with objects which define toRsconf and a constructor taking a oRemiLib::RSConf::RSValue. Union types are also supported, including unions with nil. If multiple types in a union parse correctly, it is undefined which one will be chosen.

To change how individual instance variables are parsed and serialized, the annotation RemiLib::RSConf::Field can be placed on the instance variable. Annotating property, getter and setter macros is also allowed.

require "libremiliacr"
alias RSConf = RemiLib::RSConf

class A
  include RSConf::Serializable

  @[RSConf::Field(key: "my_key", emitNull: true)]
  getter a : Int32?
end

RemiLib::RSConf::Field properties:

Deserialization also respects default values of variables:

require "libremiliacr"
alias RSConf = RemiLib::RSConf

struct A
  include RSConf::Serializable
  @a : Int32
  @b : Float64 = 1.0
end

data = RSConf::Parser.parse(%|a = 1|)
A.fromRsconf(data) # => A(@a=1, @b=1.0)

Extensions: RemiLib::RSConf::Serializable::Strict and

RemiLib::RSConf::Serializable::Unmapped.

If the RemiLib::RSConf::Serializable::Strict module is included, unknown properties in the RSConf document will raise a parse exception. By default the unknown properties are silently ignored. If the RemiLib::RSConf::Serializable::Unmapped module is included, unknown properties in the RSConf document will be stored in a Hash(String, RemiLib::RSConf::RSValue). On serialization, any keys inside rsconfUnmapped will be serialized and appended to the current RSConf object.

require "libremiliacr"
alias RSConf = RemiLib::RSConf

struct A
  include RSConf::Serializable
  include RSConf::Serializable::Unmapped
  @a : Int32
end

data = RSConf::Parser.parse($|a = 1, b = 2|)
a = A.fromRsconf(data) # => A(@rsconfUnmapped={"b" => 2}, @a=1)
a.rsconfUnmapped["b"].raw.class   # => Int64

Class annotation RemiLib::RSConf::Serializable::Options

Supported properties:

require "libremiliacr"
alias RSConf = RemiLib::RSConf

@[RSConf::Serializable::Options(emitNulls: true)]
class A
  include RSConf::Serializable
  @a : Int32?
end

#after_initialize method

#after_initialize is a method that runs after an instance is deserialized from RSConf. It can be used as a hook to post-process the initialized object.

Example:

require "libremiliacr"
alias RSConf = RemiLib::RSConf

class Person
  include RSConf::Serializable
  getter name : String

  def after_initialize
    @name = @name.upcase
  end
end

data = RSConf::Parser.parse("name: jane")
person = Person.fromRsconf(data)
person.name # => "JANE"

Defined in:

remilib/rsconf/serializable.cr

Constructors

Instance Method Summary

Constructor Detail

def self.new(*, __fromRSConfTopLevel toplevel : RemiLib::RSConf::RSValue) #

Called internally to perform the actual deserialization from an RemiLib::RSConf::RSValue.


[View source]

Instance Method Detail

def after_initialize #

Called after deserialization is completed.


[View source]
def afterToRsconf(builder : RemiLib::RSConf::Builder) : Nil #

Called immediately after this object is serialized to RSConf.


[View source]
def beforeToRsconf(builder : RemiLib::RSConf::Builder) : Nil #

Called immediately before this object is serialized to RSConf.


[View source]
def toRsconf(builder : RemiLib::RSConf::Builder) #

Serializes this instance to RSConf data.


[View source]