std/encoding
Encoding and decoding: what other languages need reflection for (serialization, config mapping, database rows,
schemas, --help texts).
const json = Json()
const text = json.encode user
const back = json.decode<User>(text)?
A value is its constructor call. The compiler knows every type's constructor and offers it in three forms:
written (Encode), read (Decode) and described without a value (Describe). A format (Json, a database
driver, a command line parser) implements Encoder, Decoder or Describer and never sees a type. There is no tree
in between: a value is written while the type describes itself, and nothing is lost on the way.
All three forms are generated for a type whose constructor is usable from outside, over exactly the constructor's
parameters: a private field with a default is not one of them, so a cache stays out without an annotation. What
the compiler generates is ordinary code over the vocabulary, and could be written by hand:
extend User with Encode {
fn encode<Target: Encoder>(var target: Target) {
target.record "app/User"
target.field "name"
name.encode target
target.field "tags"
tags.encode target
target.finish()
}
}
The three traits take their target as a bound, not as a trait type: a format hands its own encoder over as a
var path and reads the result out of it afterwards, and the derived code is a direct call chain with no table.
EncodedValue is what a program holds where it has left the type behind, and Structure is a type's description as
a value. docs/design/ENCODING.md is the design.
This package also has the plainer kind of encoding: bytes as text and back. Base64Alphabet, Base32Alphabet and
Bytes.hexEncoded/String.hexDecoded/String.base64Decoded are RFC 4648, unrelated to Encode/Decode above - a value's own Encoder.bytes writes
raw bytes, and a format reaches for one of these only where the wire itself is text (a JWT, a !!binary YAML
scalar, a TOTP secret).
Modules
std/encoding/base32Base32 (RFC 4648 sections 6 and 7): [Base32Alphabet.Standard] (A-Z,2-7), what NATS NKeys and a TOTP secret are written in, and [Base32Alphabet.Extended] (0-9,A-V), which sorts the same as the bytes it stands for.std/encoding/base64Base64 (RFC 4648 sections 4 and 5): [Base64Alphabet.Standard] (+,/, everywhere nothing says otherwise) and [Base64Alphabet.UrlSafe] (-,_, which need no escaping in a URL or a file name - a JSON Web Token's segments, a JSON Web Key's modulus), each with or without the=padding.std/encoding/derivedThe steps a generatedencode,decodeanddescribeare made of.std/encoding/libEncoding and decoding: what other languages need reflection for (serialization, config mapping, database rows, schemas,--helptexts).std/encoding/naming[Naming]: how a format spells the field names a type declares.std/encoding/structureA type's structure as a value: [Structure], the [Structures] describer that builds one, and the [FieldDescription] every field of a description carries.std/encoding/valuesA value without its type: [EncodedValue], the [Values] encoder that builds one, and the [ValueDecoder] that reads a typed value back out of one.
Everything
- extend
ArrayList<Item> with DecodeAnArrayListreads back as the list it is written as - a sequence, item by item - so a field of one does not keep the type around it from having a deriveddecode(Chunkof the bytecode, whose code is one). - extend
ArrayList<Item> with DescribeAnArrayListdescribes as thesequenceofList. - type
Base32AlphabetWhich of RFC 4648's two Base32 alphabets a text is written in. - type
Base64AlphabetWhich of RFC 4648's two Base64 alphabets a text is written in. - extend
Bool with Encode, Decode, DescribeBoolis the vocabulary's ownbool, in all three forms. - extend
Buffer<Item> with DecodeABufferreads back as the list it is written as, for the reason anArrayListdoes: a field of one,Bytesin the first place, does not keep the type around it from having a deriveddecode. - extend
Buffer<Item> with DescribeABufferdescribes as thesequenceofList. - extend
BytesThe operations on bytes and text that are RFC 4648's, written where they are imported from: a member another package names is found in the module of the package that is imported, souse Buffer.hexEncoded from "std/encoding"needs them here. - extend
Char with Encode, Decode, DescribeAChartravels as a text of one character: the formats of the language have no character of their own. - extend
Decimal with Encode, Decode, DescribeDecimalis the vocabulary's owndecimal: an exact number stays exact in a format that can say so. - trait
DecodeA value reads itself back. - fn
decodeAbandonA failure that ends reading the open record, the case or the tuple before its end - a source that cannot answer which field is there, a case the type does not have: it is closed, and the failure joins the problems noted so far. - fn
decodeDefaultedThe default of a field the input does not have, as the answer a read would have given. - fn
decodeEndCloses the record, the case or the tuple that was read, and fails with every problem noted on the way - oneDecodeErrorwhoseproblemslists them - or succeeds where there was none. - type
DecodeErrorWhat went wrong reading a value, with the whole chain of fields and positions it went wrong in:items[2].price.currency: a value is needed. - fn
decodeFieldValueThe value of the field [decodeHasField] positioned on, read with its owndecode. - fn
decodeFinishCloses the record, the variant or the tuple that was read. - fn
decodeHasFieldPositions on a field that has a default, and answers whether the input has it. - fn
decodeHasPrivateField[decodeHasField] for a field that is no parameter of the constructor from outside:false, and so its default, unless the source reads every field ([Decoder.readsPrivateFields]) and the input has it. - fn
decodeItemOne position of a tuple. - fn
decodeLiteralA literal type is read as its base and then checked against the values it allows. - fn
decodeMissingA field the input has to have and does not: the problem it is, noted like any other. - fn
decodeNoteNotes what reading one field or position answered: nothing for a value, and every problem of a failure, which a nested record or a sequence brings along with their whole paths. - fn
decodeProblemsThe problems a deriveddecodehas collected: none yet, where a record, a case or a tuple was opened. - trait
DecoderThe reading half of a format. - fn
decodeRecordOpens the record the constructor is read from. - fn
decodeRequiredA field the input has to have, read with its owndecode. - fn
decodeSequenceOpens the sequence a tuple is read from. - fn
decodeThroughA capsule read through its conversion pair: the source's owndecode, then the total way in. - fn
decodeThroughCheckedA capsule read through a fallible way in: the check the factory exists to force runs for a value out of a document too, and its failure is theDecodeError. - fn
decodeVariantOpens a type with cases and answers the name of the case that is there. - trait
DescribeA type describes its structure without a value: what schema-driven formats need (a DDL statement, a.protofile, a JSON Schema, a--helptext). - fn
describeCaseOne case of the open variant. - fn
describeConstantFieldOne field whose default is a constant, written into the description as data. - fn
describeDefaultedFieldOne field whose default is not data a description can hold: a call, or a value that is not a constant. - fn
describeFieldOne field that has to be there: its name, its doc comment, and its value's own description. - fn
describeFinishCloses what the last of the steps above opened. - trait
DescriberThe describing half: the same method names as [Encoder], without values. - fn
describeRecordOpens the description of a record. - fn
describeThroughA type that is described as another one: a capsule as its source, a literal type as its base. - fn
describeVariantOpens the description of a type with cases, as [describeRecord] does. - trait
EncodeA value writes itself into any format. - type
EncodedFieldOne named field of an [EncodedValue.Record] or [EncodedValue.Variant]. - type
EncodedValueAnyEncodevalue, held without its type. - extend
EncodedValue with EncodeAnEncodedValuewrites itself into any encoder, which is what makes it useful: a captured value can be bound as a SQL parameter, and a document nobody has a type for can be written out again. - fn
encodeFieldOne field of a record or a case: its name, then its value's ownencode. - fn
encodeFinishCloses what the last of the steps above opened. - fn
encodeItemOne position of a tuple: its value's ownencode. - fn
encodePrivateFieldA field that is no parameter of the constructor from outside -private, with a default - written like any other field, but only for a target that asks for every field ([Encoder.writesPrivateFields]). - trait
EncoderThe writing half of a format. - fn
encodeRecordOpens the record a value oftypeNameis written as. - fn
encodeSequenceOpens the sequence a tuple is written as. - fn
encodeThroughA capsule is written as the source of its conversion pair:Wire.from(value), then that value's ownencode. - fn
encodeVariantOpens the casenameof a type with cases. - type
EncodingErrorBytes or text that do not fit the encoding being read: what was wrong, and the character it was found at. - type
FieldDefaultWhether a field may be missing from the input, and what it is then. - type
FieldDescriptionWhat the compiler knows about one constructor parameter, and what a schema or a help text needs of it. - extend
Flags<Case> with EncodeFlags are their mask, a number, unless the target asks for names ([Encoder.flagsAsNames]): then they are a sequence of the case names, each through the case's ownencode, the lowest bit first. - extend
Flags<Case> with DecodeThe way back of [Flags]'encode: a mask throughfromBits, which refuses a bit no case stands for, or - where the source asks for names ([Decoder.flagsAsNames]) - a sequence of case names, each through the case's owndecode. - extend
Float32 with Encode, DescribeAFloat32travels as aFloat64, which holds it exactly. - extend
Float64 with Encode, Decode, DescribeFloat64is the vocabulary's ownfloat, in all three forms. - trait
FormatWhat a whole format is, once: bytes in both directions, and the twoStages that make it work on a stream. - extend
Int16 with Encode, Decode, DescribeA narrow integer travels as anInt64and is checked on the way back: a value that does not fit is an error. - extend
Int32 with Encode, Decode, DescribeA narrow integer travels as anInt64and is checked on the way back: a value that does not fit is an error. - extend
Int64 with Encode, Decode, DescribeInt64is the vocabulary's ownint, in all three forms. - extend
Int8 with Encode, Decode, DescribeA narrow integer travels as anInt64and is checked on the way back: a value that does not fit is an error. - extend
List<Item> with EncodeA list is asequence: its length in front, then every item with its ownencode. - extend
List<Item> with DecodeA sequence, item by item, each through the item's owndecode. - extend
List<Item> with DescribeA list describes as asequencearound its item's structure: the shape is one item, repeated. - extend
Map<Key, Value> with EncodeA map is amap: its length in front, then every entry as its key and its value. - extend
Map<Key, Value> with DecodeA map, entry by entry: a key, then its value. - extend
Map<Key, Value> with DescribeA map describes as amaparound its key's and its value's structure. - type
NamingHow a format writes a field name. - extend
Option<Value> with EncodeSomeis its value, andNoneisnothing()- which a field may leave out, so its default applies. - extend
Option<Value> with DecodeA "nothing" isNone, and anything else is the value's owndecode. - extend
Option<Value> with DescribeAn optional value describes asoptional()around the value's own structure. - fn
renderedAnyEncodevalue as readable text, for messages and debugging:User(name: "Ada", tags: ["math"]). - extend
Set<Item> with EncodeA set is a sequence of its items. - extend
Set<Item> with DecodeA sequence read into a set: an item that is there twice is there once. - extend
Set<Item> with DescribeA set describes as a sequence of its item. - extend
StringThe operations on text that read bytes back out of RFC 4648 text: hexadecimal and Base64. - extend
String with Encode, Decode, DescribeStringis the vocabulary's ownstring, in all three forms. - type
StructureWhat a [Describe] walk builds when a format wants a value instead of a visitor. - type
StructureCaseOne case of a [Structure.Variant]: its name and the structure of its own fields. - type
StructureFieldOne field of a [Structure.Record]: its description and the structure of the value it holds. - fn
structureOfThe structure of a type, as a value. - type
StructuresADescriberthat builds a [Structure]. - extend
UInt16 with Encode, Decode, DescribeA narrow unsigned integer travels as anInt64, which holds every one of its values, and is checked on the way back. - extend
UInt32 with Encode, Decode, DescribeA narrow unsigned integer travels as anInt64, which holds every one of its values, and is checked on the way back. - extend
UInt64 with Encode, Decode, DescribeUInt64is the vocabulary's ownunsigned: its upper half does not fit into anInt64. - extend
UInt8 with Encode, Decode, DescribeA narrow unsigned integer travels as anInt64, which holds every one of its values, and is checked on the way back. - fn
unknownCaseWhat a case name the type does not have is:`Lost` is not a case of `Status`. - type
ValueDecoderADecoderover an [EncodedValue]. - type
ValuesAnEncoderthat builds an [EncodedValue].