Skip to content

Instantly share code, notes, and snippets.

@jorendorff
Created March 20, 2019 15:20
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save jorendorff/b7d3802d36db2c86c0b4c04d41b72f29 to your computer and use it in GitHub Desktop.
Save jorendorff/b7d3802d36db2c86c0b4c04d41b72f29 to your computer and use it in GitHub Desktop.

Feedback on static ("v3") decorators

Please thank littledan and the other champions for (in short) doing everything right.

I'm convinced static ("v3") decorators are not the way forward.

I think the concrete disadvantages of a static design should be taken more into account:

  • Complexity - There's currently only a sketch of the spec; it's going to be big.
  • Amount of new syntax.
  • New primitive decorators are impossible to polyfill.
  • Decorators aren't values and thus mostly can't interact with the rest of the language. For example, they can't be arguments, so no higher-order decorators. And this forces duplication in the spec everywhere we do want to be able to talk about decorators: decorator-specific syntax and semantics in import and export, for example.
  • No dynamic access to decorators, e.g. via module namespace objects. You can't dynamically import() a module to use a decorator.
  • No conditional or other dynamic definition of decorators.
  • So primitive decorators can't meaningfully be feature-tested. (You can test, but what good is it knowing the feature isn't there?)
  • TC39 and implementors impose an unwanted delay on, and have an unwanted role as gatekeeper over, new primitive decorators.
  • Hard choice for users between accepting the delay and running everything through Babel forever.

Maybe I don't properly understand the purported benefits of static decorators.

  • No specific performance benefits are claimed, but the proposal suggests that Babel sees significant code size improvements, for example. I'll be surprised if similar gains could not be had with less dramatic changes (and without the difficulties listed above).

    Measuring the size of Babel output probably isn't a good metric by itself anyway. Consider: The main thrust of this design is to make some information statically available at a particular moment in time: after decorator import dependencies are loaded, but before the code starts running. The proposal, effectively, is that all high-performance implementations converge on doing bytecode generation at this time. It's possible that Babel benefits, yet in engines where modules load over the Web, this change actually punishes code that uses decorators (by delaying some work).

    Delaying bytecode generation has other technical problems. Currently ASTs are short-lived; the proposed implementation technique requires us to keep them around while dependencies are loading. Currently module bytecode is a function of the module source, so it is easy to cache; the proposal suggests making bytecode depend on decorators imported from other modules.

    Stepping back a bit, high-level features should not be warped around implementation details to this extent.

  • The new design is meant to make it easier to define new decorators. But again, a modest change to "v2 decorators" with the same goal would yield similar benefits, right? The proposal includes this example code:

    // bound.mjs
    export decorator @bound {
      @register((target, name) => {
        ...
      })
    }
    

    But we could just as well say it like this:

    // bound.mjs
    export bound = Decorator.register((target, name) => {
      ...
    });
    

    which is already syntactically valid ES.

A possible way forward is to evolve v2 decorators. Change the interface so that all decorators work like v3 @register. More intermediate states of the class are visible, but there's less messing around with descriptors. Maybe add a few helper functions, like Decorator.wrapMethod(f => f') and Decorator.compose(...decorators).


Jason Orendorff
20 March 2019

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment