JSON and LosslessNumber types
From #244:
I was disappointed that
LosslessNumber instance of Numberis false, also I get weird type errors from lossless-json, I had to add anany(dis a string):const dataAsLosslessJson = losslessJsonParse(d); jsonDataString = "json_data = " + objToPython(dataAsLosslessJson as any) + "\n";if I remove the
as any, I get a type error fromobjToPythonsayingArgument of type 'unknown' is not assignable to parameter of type 'string | number | boolean | object | null'. ts(2345). Why does it thinkdataAsLosslessJsonisunknown?
I'm a bit struggling with defining types for the library. For example the native JSON.parse is in my IDE giving the following TypeScript types:
interface JSON {
parse(text: string, reviver?: (this: any, key: string, value: any) => any): any;
}
Which is quite generic.
We can define JSON like:
https://github.com/josdejong/lossless-json/blob/94d906cf255123e82a57b44bcc6ed0c6923599ec/src/types.ts#L1-L7
But as soon as we have a reviver and/or numberParser, the output can be sort of anything. I tried to represent this as:
https://github.com/josdejong/lossless-json/blob/94d906cf255123e82a57b44bcc6ed0c6923599ec/src/types.ts#L9-L15
So, there are two different levels of JSON, but what types can really come out of the function depend on the reviver and numberParser. Maybe with generics it is possible to define this strictly instead of relying on unknown (which covers LosselessNumber and anything).
Now, as for your specific questions and ideas:
- The output of
LosslessJSON.parse()is aJavaScriptValue. Your functionobjToPython(obj: string | number | boolean | object | null, indent = 0)does not accept the more broad definition ofJavaScriptValueso it makes sense that TypeScript complains about that. I guess the logic solution is to make the first argument ofobjToPythoncompatible withJavaScriptValue. Or we have to be able to - It is an interesting idea to make
LosslessNumberextendNumber. I have to think that through a bit. It would make the wrapper class less lightweight: we would have to add all methods thatNumberhas. But it can make usage more natural, and maybe we could makeJSON.parsereturnJSONValueinstead ofJavaScriptValuesomehow 🤔