Skip to content

Commit ca75a01

Browse files
committed
docs: add documentation for field and structure serialization hooks
Refs: #15
1 parent ee73c8e commit ca75a01

File tree

1 file changed

+84
-2
lines changed

1 file changed

+84
-2
lines changed

docs/advanced/annotations.md

Lines changed: 84 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -18,8 +18,7 @@ generated structure, the field annotations are collected and the individual vali
1818

1919
## Converter Supplier
2020

21-
Using the `ConverterSupplyingVisitor` interface, you can create a converter supplying visitor that
22-
can supply a converter for a given field.
21+
Using the `ConverterSupplyingVisitor` interface, you can supply a converter for the annotated field.
2322

2423
## Code Examples
2524

@@ -34,4 +33,87 @@ if (supplier != null) {
3433
``` { .dart title="Getting multiple class annotations"}
3534
DogStructure structure; /* Get structure here*/
3635
var classValidators = structure.annotationsOf<ClassValidator>().toList();
36+
```
37+
38+
## Hooks
39+
### Field Hooks
40+
41+
Field hooks enable fine-grained control over the serialization of individual fields.
42+
They are implemented by mixing in the `FieldSerializationHook` interface on a
43+
class that also implements `StructureMetadata`.
44+
45+
Field hooks are executed for structure converters when using the `NativeSerializerMode`.
46+
They receive the field context and are able to modify the serialized map after a
47+
field has been serialized as well as before it is deserialized.
48+
49+
``` {.dart title="Field Serialization Hook Example" }
50+
class MultiplyByTwo extends StructureMetadata with FieldSerializationHook {
51+
const MultiplyByTwo();
52+
53+
@override
54+
void postFieldSerialization(
55+
NativeStructureContext context,
56+
NativeStructureFieldContext fieldContext,
57+
Map<String, dynamic> map,
58+
DogEngine engine) {
59+
final value = map[fieldContext.key] as int?;
60+
if (value != null) map[fieldContext.key] = value * 2;
61+
}
62+
63+
@override
64+
void beforeFieldDeserialization(
65+
NativeStructureContext context,
66+
NativeStructureFieldContext fieldContext,
67+
Map<String, dynamic> map,
68+
DogEngine engine) {
69+
final value = map[fieldContext.key] as int?;
70+
if (value != null) map[fieldContext.key] = value ~/ 2;
71+
}
72+
}
73+
```
74+
75+
The hook can then be applied to a field like any other annotation:
76+
77+
``` { .dart .focus hl_lines="4-5" }
78+
@serializable
79+
class Example with Dataclass<Example> {
80+
81+
@MultiplyByTwo()
82+
int number;
83+
84+
Example(this.number);
85+
}
86+
```
87+
88+
### Structure Hooks
89+
90+
Structure hooks operate on the entire serialized map of a class. They are implemented by extending the
91+
`SerializationHook` class or implementing it. You can apply them to a structure by annotating the class with the
92+
annotation that extends `SerializationHook`.
93+
94+
Structure hooks are executed for structure converters when using the `NativeSerializerMode`.
95+
They receive the full structure map and can freely modify it before deserialization or after serialization.
96+
97+
98+
``` {.dart title="Structure Serialization Hook Example" }
99+
class ExampleHook extends SerializationHook {
100+
const ExampleHook();
101+
102+
@override
103+
void beforeDeserialization(
104+
Map<String, dynamic> map,
105+
DogStructure structure,
106+
DogEngine engine) {
107+
map['decoded_at'] ??= DateTime.now().toIso8601String();
108+
}
109+
110+
@override
111+
void postSerialization(
112+
dynamic obj,
113+
Map<String, dynamic> map,
114+
DogStructure structure,
115+
DogEngine engine) {
116+
map['encoded_at'] ??= DateTime.now().toIso8601String();
117+
}
118+
}
37119
```

0 commit comments

Comments
 (0)