rdking / ClassicJS

Adds full private & protected support over ES6 classes without blocking Proxy.
6 stars 1 forks source link

`class`-based syntax #5

Open trusktr opened 4 years ago

trusktr commented 4 years ago

Very interesting!

I noticed the classes don't have the empty bodies. F.e. isn't the following required?

class Ex extends Classic({...}) {};

(that last {} part)

I wonder if we can make a more familiar syntax with regular class extension and decorators. F.e.

class Ex extends Classic(Base) {
  @private foo = 123
}

The latest Babel decorators give us the initializer functions, which could internally be user for INIT.

I haven't looked at the impl or tested it yet. Will do soon!

trusktr commented 4 years ago

Hmmm, I wonder if it is possible to go a step further with the decorators, and path the class without needing extends Classic. F.e.

@encapsulated
class Ex extends HTMLElement {
  @private foo = 123
  @protected bar = 42
  constructor() {
    super() // what about this part?

    console.log(this.__foo)
  }
}
trusktr commented 4 years ago

The nice thing about decorators is it would be easy to switch between both forms. F.e. in dev mode we use decorators to enforce contracts, in prod mode we can strip them (make them no-ops). Or f.e. someone can opt to take them off if they really need performance for some particular case (regardless of a dev mode) as a reasonable trade off, and not have to radically convert syntax.

rdking commented 4 years ago

I've updated README.md. That was written based on the original idea ClassicJS evolved from. Back then, I was thinking about how to extend my approach for injecting data into a class definition to also cover private data. Starting with class .... isn't necessary. ClassicJS allows you to just use the Classic function to declare a class. I face palmed myself half-way through the development of this code when I realized that.

rdking commented 4 years ago

I wish they didn't dispose of the first decorators proposal. That was powerful enough that I could write a decorator library to fix all the design mistakes and omissions without needing to create a completely different approach to defining classes. Oh well. I tried with the new watered-down decorators, but there simply isn't any way to properly manage private data. Without being able to redefine the structure of the class during construction, there's no way to avoid all the issues they've created.

trusktr commented 4 years ago

Without being able to redefine the structure of the class during construction, there's no way to avoid all the issues they've created.

If a class decorator returns a subclass, we can't redefine the shape in there?

EDIT: I'm talking about the latest decorators in Babel, which I call "v2", and the latest proposal-decorators that got put on pause I call "v3"

rdking commented 4 years ago

Given that I tend to avoid Babel like the plague, I'm not certain what the latest is in there. If it still resembles the v1 proposal, then it can do the job, as that version could override, add, and remove the individual declarations in the class. If it's more like the current (albeit stalled) proposal, then it's hopeless. If a decorator ends up returning a subclass, that would have to be a class-level decorator, otherwise the subclass would just end up being a member of the declared class. Either way, you'd be introducing a bit of a surprise. It would also depend on what you do with the subclass. Lots more variables involved doing that.

trusktr commented 4 years ago

The current Babel decorators (which I call v2) can do everything the original (legacy, v1) decorator can do. Babel doesn't have the current stalled decorator (v3).

So a class decorator can do this in Babel:

@foo
class Foo {}

where the foo decorator can effectively return class Decorated extends Foo {...}.

rdking commented 4 years ago

If v2 is still as good as legacy, then I'm going to run an experiment and create a few decorators for making classes as good as ClassicJS:

I'd also like to desugar private fields into my style of WeakMap access. The way they do it is just too cumbersome. However, that's a little beyond what you can reasonably do with decorators.