♻️ Extensions to the ECMAScript syntax

I think it is relevant to keep track of proposals and other works that involves extending the ECMAScript syntax in one thread.

Example: Personally, I wanted to explore uses for : and {[]} around live bindings and safely-coercing imported bindings.

import {:exports:/} from 'package'

Without getting into details, I am revisiting the current reality where we assume that modules can only ever export valid ECMAScript binding identifier names.


Let’s say that we can all agree that we can only export valid binding identifier names from ESM code, and that being so because the respective declarations must have valid ECMAScript binding identifiers names — certainly, a possible way to look at the same thing and leave ESM matters be.

In this view, we need a way to safely define explicit forms of scoped binding identities (aka not identifier names):

  • Where «:» signifies scoped bindings against synthetic namespaces (ie JSON for one, but also CJS et al).

    Where « and » denote “no space here” for grammar productions.

  • It could be prefixed:… for aliasing to avoid clashing

    Binding { a:1 } from 'a' and { b:1 } from 'b'.

    Certainly, restricting it to { «:» as «ImportedBinding» } in ESM is a safer place to start.

  • It can also offer magical powers in the future, like:

    Binding { :1 as one } against synthetically namespaced arrays!

    Binding { :[1,3,5] as many } to synthesize bound scopes — ie not duplicated elements — but have a Symbol.iterator for Array.from(many) goodness with actual values not bindings — ie [... many] creates ['a', 'b', 'c'] of the , and {… many} creates {1: 'a', 3: 'b', 5: 'c').

    Binding { :matches(/^regexp/) as query } to synthesize bound scopes — shorthand matching { :/^regexp/i as query } — where it can also still have Symbol.iterator goodness for the entries or the values — detail at this point.

    And lastly, export { : } from 'loader#require:cjs:from:esm' — which would export the entire bound scope instead of the usual namespace and that would be okay even in ESM if they can work with { «:» as «ImportedBinding» } or better yet if we first-class «ScopedBindingIdentities» under «IdentifierReference» production.

In short, there is a lot about bindings that we are missing out on maybe because of nothing more than circular discourse that is saturating the role of ‹IdentifierName› in the specs in ‹ExportSpecifier› versus ‹ImportSpecifier›.

Worth noting that I proposed considering : as an alternative ~., and so if that ends up being considered for eventual send or other proposals, we can switch to :: only as the first significant token of a scoped binding — eg prefix::1:2:3 or starting ::1:2:3… etc.

export default {[...live_bindings]}

This one is covered in depth here:

But do {[]} and : even work?

I’m inclined to say it does, and as soon as we make enough headway on constructs in experimental markup, we can explore this and similar matters more confidently.

Insanity Checks

:ballot_box_with_check: They throw on any runtime that does not support it.

:ballot_box_with_check: They can safely coincide with all existing production forms with token overlapping.