Module: Jinx::JSON::Serializable

Defined in:
lib/jinx/json/serializable.rb

Overview

Serializable is the JSON serializer Resource mix-in.

#to_json creates a JSON string from a jinxed object. The JSON payload is suitable for transfer to a remote Deserializer. This Serializable module is included directly in the jinxed application domain module after including Resource, e.g.:

module MyApp
  include Jinx::JSON::Serializable, Jinx:Resource

which includes Resource followed by the Serializable.

The module which includes Serializable is extended with the Importer, which enables deserialization of the serialized JSON.

The JSON payload is built as follows:

  • non-domain properties are serialized

  • dependent references are serialized recursively

  • independent reference primary and secondary key content is serialized

  • circular references are precluded by truncating the reference with a surrogate object id

Class Method Summary collapse

Instance Method Summary collapse

Class Method Details

.included(other) ⇒ Object



30
31
32
33
34
35
36
37
# File 'lib/jinx/json/serializable.rb', line 30

def self.included(other)
  super
  if Class === other then
    other.extend(Deserializer)
  else
    other.extend(Deserializable)
  end
end

Instance Method Details

#json_class_nameString (private)

The JSON class name must be scoped by the Resource package module, not the Java package, in order to recognize the Jinx::Resource JSON hooks.

Returns:

  • (String)

    the class name qualified by the Resource package module name context



57
58
59
# File 'lib/jinx/json/serializable.rb', line 57

def json_class_name
  [self.class.domain_module, self.class.name.demodulize].join('::')
end

#json_value_hash(visited) ⇒ {Symbol => Object} (private)

Builds a serializable attribute => value hash with content as follows:

  • If this domain object has not yet been visited, then the hash includes all attributes, as well as the Jinx::Resource#proxy_object_id.

  • If this domain object has already been visited, then the hash includes only the proxy_object_id.

Each Set attribute value is converted to an array, since JSON does not serialize a Set properly.

The Deserializer is responsible for reconstituting the domain object graph from the serialized content.

Parameters:

  • visited (<Resource>)

    the serialized objects

Returns:

  • ({Symbol => Object})

    the serializable value hash



74
75
76
77
78
79
80
81
82
83
84
85
# File 'lib/jinx/json/serializable.rb', line 74

def json_value_hash(visited)
  # If already visited, then the only content is the object id.
  if visited.include?(self) then
    return {:object_id => proxy_object_id}
  end
  visited << self
  vh = value_hash(self.class.java_attributes)
  vh.each { |pa, v| vh[pa] = v.to_a if Set === v } 
  # Add the object id.
  vh[:object_id] = proxy_object_id
  vh
end

#to_json(state = nil) ⇒ String

Returns the JSON representation of this Resource.

Parameters:

  • state (State, Hash, nil) (defaults to: nil)

    the JSON state or serialization options

Returns:

  • (String)

    the JSON representation of this Resource



41
42
43
44
45
46
47
48
49
# File 'lib/jinx/json/serializable.rb', line 41

def to_json(state=nil)
  # Make a new State from the options if this is a top-level call.
  state = State.for(state) unless State === state
  # the JSON content
  {
    'json_class' => json_class_name,
    'data' => json_value_hash(state.visited)
  }.to_json(state)
end