Allen Wirfs-Brock wrote:
OK, I ready you proposal.  I'll summaries it:

class Sub extends Super {
    constructor (...args) {
        super(...args);  //or super.constructor(...args)  because they mean the 
same thing.
   }
}

creates an (almost) ordinary object that is the initial value of the Sub binding.  The 
[[Prototype]] of Sub is the value of Super. Sub is created with a "prototype" property 
whose value is a new ordinary object whose [[Prototype]] values is Super.prototype.  Sub.prototype 
has a method property named "constructor" whose value is a super bound method function 
with the user specified body.  There is nothing special about this method, it it just like any 
other method defined in a class declaration.  In particular it does not have a [[Construct]] 
internal property.

The only thing exotic about Sub is that the object has a [[Construct]] internal 
method.  It does not have a [[Call]] internal method.  The definition of its 
[[Construct]] in almost JS pseudo code is:

       //internal method  this.[[Constructor]](argList):
       let newObj = this.@@create();  //eg Sub.@@create();
       let replacementObj = this.prototype.constructor.apply(newObj, argList);
       if (typeof replacementObj == "object"&&  replacementObj !== null) return 
replacementObj
       return newObj;

Implications:
    Sub === Sub.prototype.constructor evaluates to false.
    To create a new instance of Sub say:
            new Sub()
    The following is a TypeError, because Sub does not have a [[Call]] internal 
method:
           Sub()
    The following is a TypeError, because Sub.prototype.constructor does not 
have a [[Construct]] internal method:
            new Sub.prototype.constructor()
     Sub.prototype.constructor can be called directly or as a method invocation 
including via a super call a subclass of Sub.

It seems to me, all you have accomplished here is to make it illegal
to call a class object directly as a function. If we were starting

From technical PoV*, yes.
Oh, and I fixed the super / new inconsistency.

over that might be a reasonable design choice. But we have a legacy
to consider. Even if we think we should discourage direct calls to

Ignoring Foo.call(this) replacable by super, mostly, "class" is used for new Foo and for Foo.staticVar. I argued the change is big in its wider implication, even scary, maybe (but I see it as in fact minimal), but should not (imo) beat legacy much; because the fact of the tight coupling was not exploited so much.

class objects (I think I'm now in that camp) actually making it an
error seems like it may be too big of a step away from the legacy
conventions.

And there is no better time to do that step than now, when class is new construct in the language.

*There is more than narrow technical PoV. By returning plain object with exotic [[Construct]], working in nearly every detail as a class, while affording not to be the constructor itself, you effective say openly "You can use any [[Construct]]ified object as a class in ES6+. Gates are finally open".

It can be blessed by Reflect.makeClass(classObject, protoObject) or similar API.

It can bring lots of new patterns and cowpaths into the language.
If people don't want plain object to be the class, but their existing object x, they do
  Reflect.makeClass(x, (class {...}).prototype);

and they then can `new x`. They choose what they will use as x for new operator; because now class is one object and constructor is another.

For example, the criticized pattern of 'function that does differently for [[Call]] and [[Construct]]' could now be created as well. Just 'makeClass' it.


The main message of this proposal is that beyond fixing super/new inconsistency, it opens new world for "classes", not restricted by the legacy tightly bound class===constructor objects.

And by making class to return this kind of 'decoupled' classes, this widened view to "who may be used as a class in new / extends?" is effectively blessed.

You cannot open it later. Because there will be lagacy code that already uses `class`.

(I'd stress again, that, imo, that change is very little, too little for the fruits it can bear. Fix me if it breaks something critical)

Allen

Herby
_______________________________________________
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss

Reply via email to