Improve docs for non-default data types
jasongerbes opened this issue · 1 comments
The superjson README provides a recipe for registering a custom transformer for a non-default data type:
import { Decimal } from "decimal.js"
SuperJSON.registerCustom<Decimal, string>(
{
isApplicable: (v): v is Decimal => Decimal.isDecimal(v),
serialize: v => v.toJSON(),
deserialize: v => new Decimal(v),
},
'decimal.js'
);
However, the docs don't include any details about the registerClass
and registerSymbol
methods, nor do they include details about how a custom transformer can leverage the built-in transformers.
For example, given a CustomMap
class the extends the built-in Map
class and adds a customProperty
and overridden get
method, how can I use registerClass
or registerCustom
in a way that leverages the built-in serialization of the Map's entires?
class CustomMap<K, V> extends Map<K, V> {
public customProperty: string;
public constructor(
customProperty: string,
entries?: ReadonlyArray<readonly [K, V]> | null
) {
super(entries);
this.customProperty = customProperty;
}
public override get(key: K): V {
const value = super.get(key);
if (!value) {
throw new Error(`Value with key ${key} does not exist.`);
}
return value;
}
}
Using registerClass(CustomMap)
doesn't serialize the CustomMap
entries:
import SuperJSON from "superjson";
SuperJSON.registerClass(CustomMap);
const map = new CustomMap([
["a", 1],
["b", 2],
]);
const { json, meta } = SuperJSON.serialize(map);
/*
json = {
customProperty: "My Map"
};
meta = {
values: [
["class", "CustomMap"]
]
};
*/
Using registerCustom
, it's unclear how you can leverage SuperJson's built-in Map transformer to serialize and deserialize the CustomMap
class:
SuperJSON.registerCustom<CustomMap<any, any>, string>(
{
isApplicable: (v): v is CustomMap<any, any> => v instanceof CustomMap,
serialize: (v) => "", // TODO
deserialize: (v) => new CustomMap(/* TODO */),
},
"CustomMap"
);
Hey @jasongerbes! registerClass
and registerCustom
aren't documented well, I agree. If you want to open a PR that adds docs for that, i'd be happy to review it!
Regarding the CustomMap
case, I don't see an easy way of leveraging SuperJSON's built-in Map transformer, either. registerCustom
is probably the best choice. You could try to make a Map
out of your CustomMap
and then recursively call SuperJSON.serialize(v)
inside of serialize
. Would that help?