Background
We have an historically toJSON
convention to automatically transform any class into its JSON representation. Times are different these days and while structuredClone
works wonderfully for all its allowed types, it's impossible from a library author point of view to grant some data can cross boundaries or be cloned properly, as opposite of throwing errors.
Proposal
const ref = {
// implicitly invoked when `structuredClone(ref)` happens
// or during the conversion / clone algorithm is applied
[Symbol.clone]() {
// returns any structured-clone compatible value
return new Map(Object.entries(this));
}
};
What does it solve?
The complexity of cross-realms interactions is over 9000 these days:
- Workers and
postMessage
implicitly usestructuredClone
to pass values around - Proxy used in foreign worlds can't survive any
postMessage
dance without explicit user interaction (i.e. use ad-hoc API to transform that proxy into something consumable elsewhere) - classes defined in a world cannot be cloned in any other world, including the very same realm they'd like to be cloned
How would it solve it?
The algorithm should look for non primitive values to a Symbol.clone
special property that should return the cloned representation of the underlying proxy, class, complex data, and so on.
For this proposal, to have at least something, it'd be a developer concern to "reconstruct" or understand that data, simply screening in a recursive way whatever was cloned, simplifying ad-hoc clones for API calls, or cross-proxy related use cases (all the WASM things I am dealing with daily from Workers, as example).
Benefits
As library author, I can dictate how any reference the library create could be cloned or even throw if some reference should actually never be cloned (authentication / credentials / passwords / security related things / ... and so on)
That's it, that's the proposal ... anyone happy to champion it?
edit I might have just realized this might be not a TC39 concern or field ... so maybe I should move this proposal to WHATWG instead ... any hint/thoughts/argument against this idea would be welcomed though, and I also think structuredClone
should be backed into JS itself, if that's not already the case, as JSON is super cool and great, but it shows its age daily (see other runtimes attempts into changing its parsing goal in a way or another).
edit if interested, I've also opened an issue in WHATWG/streams repo: Symbol.clone to ease-out structuredClone implicit conversion ยท Issue #1314 ยท whatwg/streams ยท GitHub