How to extend the schema¶
Convert a field to a domain value¶
Choose the narrowest extension mechanism that can express the format:
Goal |
Mechanism |
|---|---|
Convert one decoded value |
|
Select one of several layouts |
|
Add cases without editing the owner |
|
Generate fields at runtime |
|
Use absolute offsets or message-wide state |
hand-written outer codec |
Keep the base wire operation declarative and transform only its completed value:
import uuid
from rustruct import Struct, convert, raw
class Record(Struct):
identifier: object = convert(
raw(16),
decode=lambda value: uuid.UUID(bytes=value),
encode=lambda value: value.bytes,
)
identifier = uuid.UUID("00112233-4455-6677-8899-aabbccddeeff")
assert Record(identifier=identifier).pack() == identifier.bytes
assert Record.unpack(identifier.bytes).identifier == identifier
The callbacks receive a completed field value. They cannot move the cursor, inspect arbitrary sibling state, or change the base field’s encoded width.
Compose an algorithmic outer codec¶
Keep layout-shaped components as rustruct.Struct classes, then write only the
algorithmic layer by hand. This is appropriate when decoding depends on
absolute offsets, backward pointers, or state shared across distant fields.
The bundled DNS model follows this pattern: its name compression parser owns the message-wide cursor and suffix table, while flags and fixed RDATA types remain declarative.
Read Extension model for the design rationale and Extension API for the supported public extension points.