simpler, sweeter syntax for modules

Luke Hoban lukeh at
Wed Mar 21 15:44:15 PDT 2012

Dave - 

Great to see the updates.  A couple of questions:

>> import "foo.js" as Foo;
>> import foo from "foo.js";

These two forms look rather confusingly similar given how different they are, and the inversion of order of where the filename lives doesn't seem to line up with the semantic difference between the two forms.  It feels like this is an attempt towards fluent syntax design, but to me at least, this just doesn't feel easy to learn/remember/read.

>> module m =;

Why isn't aliasing a remote module the same as aliasing a local module?  That is, why can't I say 'module m = "foo.js"' instead of 'import "foo.js" as m'?  It seems the whole syntactic surface area of modules would be simpler if remote module identifiers were used in the same way as local module bindings in the various syntactic forms.  Since this seems to be the way things are done on the RHS of 'import...from...', why be different in 'module...=...'? I thought this is how things were originally - why change?

More broadly - is it possible to reduce further to just 'module...=...' and 'import...from...'?  Which mean "alias a module" and "import names from inside a module" respectively.


-----Original Message-----
From: es-discuss-bounces at [mailto:es-discuss-bounces at] On Behalf Of David Herman
Sent: Wednesday, March 21, 2012 3:29 PM
To: es-discuss discussion
Subject: simpler, sweeter syntax for modules


Thanks to some a-maz-ing [1] work by Andreas Rossberg (I'll spare the gory algorithmic details), the linking process no longer needs the syntactic distinction that static module bindings are only created via the `module` (contextual) keyword. This frees us up to simplify the syntax, making much less use of the `module` keyword and much more use of `import`.

I've drafted a new syntax that is both much simpler and, I think, far more intuitive than the previous version.


* importing an external module:

    import "foo.js" as Foo;

* importing a module's export:

    import foo from "foo.js";
    import bar from Bar;
    import baz from bar.mumble.quux;

* importing all exports:

    import * from Bar;

* importing with renaming:

    import { draw: drawGun }    from "cowboy.js",
           { draw: drawWidget } from "widgets.js";

* defining a module (same as ever):

    module m { ... }

* aliasing a module for convenience:

    module m =;

This new syntax is up on the wiki:

A couple conventions to note about this:

* the "as" contextual keyword signifies renaming the module *itself*

* the "from" contextual keyword always signifies extracting an export /from/ the module

* while "import" no longer strictly means extracting an export, it matches common spoken usage better -- "import" is used both to mean extracting exports /and/ loading external modules

* despite this overloading, a single "import" declaration is *only* ever importing modules or importing bindings, never both

Comments welcome [2],

[1] Really. You have no idea.
[2] Translation: Unleash the hounds of bikeshedding! ;-P

es-discuss mailing list
es-discuss at

More information about the es-discuss mailing list