Jan 29 TC39 Meeting Notes

Allen Wirfs-Brock allen at wirfs-brock.com
Fri Feb 8 10:35:37 PST 2013

On Feb 8, 2013, at 10:15 AM, Claude Pache wrote:

> Le 8 févr. 2013 à 16:00, David Bruant <bruant.d at gmail.com> a écrit :
>> Le 07/02/2013 18:42, Andreas Rossberg a écrit :
>>> On 7 February 2013 18:36, David Bruant <bruant.d at gmail.com> wrote:
>>>> I hardly understand the benefit of an inconditionally-throwing setter over a
>>>> __proto__ as data property, but I'm fine with either.
>>> Well, it _is_ a setter, and even one that modifies its receiver, not
>>> its holder. What would be the benefit of pretending it's not?
>> It _is_ an abomination (arguably, it even __is__ an abomination). Any resemblance to real ECMAScript construct, living or dead (?), is purely coincidental.
>> From the notes, a quote from Allen is "involves magic". I don't think I will surprise anyone if I say that whatever is decided for __proto__, there will be magic involved.
>> An idea that I don't think has been suggested is to stop pretending __proto__ is something else than magic:
>> $> Object.getOwnPropertyDescriptor(Object.prototype, '__proto__');
>> {
>>   magic: true,
>>   enumerable: false,
>>   configurable: true
>> }
>> Quite exotic but very clear. At will, replace "magic" with "abomination", "de facto standard", "wildcard", "don't use __proto__" or "Why did you call Object.getOwnPropertyDescriptor on __proto__ anyway?". Other better suggestions are welcome, obviously.
>> Admittedly, the last idea may be a bit long, but that's a string, so that can be an property name. I wouldn't rule it out too quickly ;-)
>> David
>> _______________________________________________
>> es-discuss mailing list
>> es-discuss at mozilla.org
>> https://mail.mozilla.org/listinfo/es-discuss
> The magic is not in the form of the '__proto__' property of the Object.prototype object, but in the action that its setter performs. Precisely, as implemented in the latest versions of Safari and Firefox (I haven't tested other browsers), Object.prototype.__proto__ acts as if it has been defined as follows:
> ;(function() {
>    var getPrototypeOf = Object.getPrototypeOf
>    Object.defineProperty(Object.prototype, '__proto__', {
>            get: function() { return getPrototypeOf(this) }
>          , set: function(p) { __setPrototypeOf__(this, p) }
>          , configurable: true
>          , enumerable: false
>    })
> })()
> where  __setPrototypeOf__(obj, p) is some function that does the following (note the second bullet):
> * throws an error if obj is not an object; otherwise,
> * throws an error if obj is not extensible; otherwise,
> * fails if p is not an object; otherwise,
> * throws an error if obj is equal to p or is in the prototype chain of p (to avoid cycles); otherwise,
> * replaces the prototype of obj with p.
> The only part not user-implementable (and the only magic, if any,) is in the "replaces the prototype of obj with p" part above.
> However, I would find reasonable to treat __proto__ similarly to eval: so that the aforementioned __setPrototypeOf__ function is allowed to fail when it has not been called with the exact syntax obj.__proto__ = something. Anything else, including obj['__proto__'] = something, could fail. Admittedly, THAT would be black magic, but again, it is not in form the property descriptor, but in the definition of __setPrototypeOf__.
> —Claude

The "magic" that was being proposed at the meeting was that
would return an accessor property descriptor whose "set" property ("and "get"??) was a function like:
     function () {throw new TypeErrorException}

This violates the mundane inherited accessor property equivalence for situations like:
     obj.__proto__ = foo;

But such a relationship between [[Get]]  or [[Set]] and [[GetOwnProperty]] has never been identified as an essential invariant and it is easy to create a proxy that does not have that behavior.  So what was proposed is only "magic" from the perspective of ordinary objects.


More information about the es-discuss mailing list