Re: JSON-serializable object

On 11/16/16 1:17 AM, Marcos Caceres wrote:
> However, it doesn't define how a UA actually would check the above...
> apart from basically calling:
> ```JS
> try {
>    JSON.parse(JSON.stringify(obj));
> } catch(err){
>    throw new Error("Not a JSON-serializable object");
> }

Not good enough.  You can easily create a proxy which will throw on 
every even-numbered call to JSON.stringify, say.

A UA _could_ check something along the lines of (for non-array objects):

1) The [[GetPrototypeOf]] of the object is

2) The prototype of the object is Object.prototype.

3) The object's [[GetOwnProperty]] is

4) The object's [[OwnPropertyKeys]] is

4) Neither the object nor Object.prototype have an accessor property 
named "toJSON", and if they have a value propety with that name then its 
value is not callable.

5) The object is not a Number object or a String object or a Boolean object.

6) The object is not callable.

7) For each string-named own property of the object, the following hold:

   a) It is a value property.
   b) The value is an object, null, a boolean, a string, or a number.
   c) If the value is an object, it is itself JSON-serializable.
   d) If the value is a number, it's finite and is not -0.

Plus some conditions around arrays that I have not dug into.  At the 
very least requires no holes and that all values satisfy item 7 above.

I make no claim that the above checks are sufficient.  For example, I 
strongly suspect that if you take a Node with no extra properties 
defined on it and Object.setPrototypeOf its prototype to 
Object.prototype then it would pass all the above tests, but presumably 
not be considered "JSON-serializable" by the dataloss condition cited. 
But the above checks are certainly necessary.

Note also that whether an object is "JSON-serializable" by this 
definition depends on some seriously non-local state...


Received on Wednesday, 16 November 2016 15:05:07 UTC