Background
- Iroha 2 peer receive messages from it clients primarily serialized in SCALE codec, but also some endpoint receive JSON messages
- Iroha 2 has some client libraries in development (Java/Kotlin, JavaScript, Python)
- Scale codec do not need the name of the properties, but JSON do need
Problem
Iroha 2 has a lot of model-objects that peer can receive as input from blockchain clients and can respond with. Currently Iroha 2 in the active development process and set of this model-objects changes very often. These changes must be reflected in the Iroha 2 client's library and it requires a lot of affords to keep client's implementation up to date.
Solution
We can generate a scheme which would introspect details of object-models. The scheme brings such benefits:
- Code generation of models and serialization/deserialization tests
- Type safe checks in clients code (if programming language support type safety)
Basically we can consider 3 types of items
1. Scalars
int: in SCALE integers can be encoded as fixed-width integer and compact integer. Compact integer itself has 4 modes. So generally we have 5 ways to serde integer (1 fixed-width + 4 modes of compact integers)
{ "type": "int", "mode": "CompactTwoByte" //possible values FixedWidth, CompactSingleByte, CompactTwoByte, CompactFourByte, CompactBigInteger, }
- bool: no tricks here
{ "type": "bool" }
2. Built-in containers
[Option / Result / Vec / typle : basically we are interested in only inner values of the container
[ { "type": "Option", "item_type": { "type" : "bool" } }, { "type": "Result", "item_type": { "type": "int", "mode": "CompactFourByte" } }, { "type": "Vec", "item_type": { "type": "bool" } }, { "type": "tuple", "items": [ { "type": "int", "mode": "CompactFourByte" }, { "type": "Option", "item_type": { "type" : "bool" } } ] } ]
3. Custom containers
- Structures: in structures declare definitions inline for built-in types and declare a reference for custom types
{ "type": "struct", "name": "Foo", "codec": "SCALE", //possible values SCALE or JSON "properties": [ { "name": "enabled", "definition": { "type": "bool" } }, { "name": "id", "definition": { "type": "struct", //reference to other struct "struct_name": "Id" } }, { "name": "counter", "definition": { "type": "int", "mode": "FixedWidth" } } ] }
- Enums: similar to Structures but also every variant of enum has a discriminator that used in Scale. By default based on 0, but can be overriden by attributes
Additional Information
- Scale codec description in Substrate docs [https://substrate.dev/docs/en/knowledgebase/advanced/codec]
- Scale codec Github page [https://github.com/paritytech/parity-scale-codec]