'Why ECMAScript ES module import do not follow destructuring standard? [duplicate]

In JavaScript I can rename and imported module this way

import { original_name as alias_name } from 'my_module'

Is there a good explanation for the need of as keyword and nod just follow the excellent destructuring standard?

Why not something like this:

import { original_name: alias_name } from 'my_module'

Just a curiosity always come to my mind



Solution 1:[1]

They do different things:

  • Destructuring is a form of property access, usually combined with a variable declaration like const, and possibly even a default initialiser
  • Importing a variable does declare an alias for a binding in the module scope

The important difference is that destructuring does run code (test object coercability, execute getters) while import declarations are fully declarative (setting up dependencies between modules, enabling cross-module hoisting even before the variables are initialised). This makes the latter statically analysable. Import aliases also have no concept of nested objects.

Both do allow "renaming", but they use different syntax for different things - it would've been too confusing otherwise. That their shorthand forms are similar to each other is mostly coincidental, caused by both using braces.

Solution 2:[2]

The answer is of course, they are different because they do different things, and only happen to have similarities in syntax.

But maybe there is a better reason why they were designed that way? I experimented with Node.JS modules in the following way:

// origin.js
export let specialNumber = 2;

setInterval(() => {
    specialNumber = Math.random();
}, 400)
// importer.js
import { specialNumber as aliasAttempt } from './origin.js'
import * as StarImport from './origin.js'
let { specialNumber: destructuringAttempt } = StarImport;

setInterval(() => {
    console.log(aliasAttempt, destructuringAttempt);
}, 400)

Here, destructuringAttempt will always give "2" (the value it got when it was destructured), whereas aliasAttempt will be keep getting changed. For example:

0.3600619094195876 2
0.33268826082163194 2
0.20684912705131553 2
0.8665522020482055 2
0.9349778920742413 2

It looks like destructuringAttempt copied by value during destructuring, whereas aliasAttempt keeps the reference to the let specialNumber variable.

(this behavior of destructuringAttempt is expected as let { specialNumber: destructuringAttempt } = StarImport; is just the same as let destructuringAttempt = StarImport.specialNumber; i.e. just copied the number)

So, maybe the reason was that, if the export is a non-const value, 'aliasing' gives a different result ("keep reference to the other variable") from typical destructuring behavior ("copy once"), therefore it's better to distinguish the syntaxes.

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1
Solution 2