ist es möglich, während des ES6-Imports etwas in das Modul mit Variablennamen zu importieren?
Das heißt Ich möchte ein Modul zur Laufzeit importieren, abhängig von den in einer Konfiguration angegebenen Werten:
import something from './utils/' + variableName;
Nicht bei der import
-Anweisung. import
und export
sind so definiert, dass sie statisch auswertbar sind und sich daher nicht auf Laufzeitinformationen verlassen können.
Sie suchen nach der loader-API (polyfill) , aber mir ist der Status der Spezifikation etwas unklar:
System.import('./utils/' + variableName).then(function(m) {
console.log(m);
});
Zusätzlich zu Felix 'Antwort werde ich ausdrücklich darauf hinweisen, dass dies derzeit von der ECMAScript 6-Grammatik nicht erlaubt ist :
ImportDeclaration:
import _ ImportClause FromClause;
import _ ModuleSpecifier;
FromClause:
- aus _ ModuleSpecifier
ModuleSpecifier:
- StringLiteral
Ein ModuleSpecifier kann nur ein StringLiteral sein, keine andere Art von Ausdruck wie ein AdditiveExpression.
Dies ist zwar kein dynamischer Import (z. B. werden in meinem Fall alle Dateien, die ich unten importiere, von webpack importiert und gebündelt, nicht zur Laufzeit ausgewählt), aber ein Muster, das ich bereits verwendet habe, kann unter Umständen hilfreich sein :
import Template1 from './Template1.js';
import Template2 from './Template2.js';
const templates = {
Template1,
Template2
};
export function getTemplate (name) {
return templates[name];
}
oder alternativ:
// index.js
export { default as Template1 } from './Template1';
export { default as Template2 } from './Template2';
// OtherComponent.js
import * as templates from './index.js'
...
// handy to be able to fall back to a default!
return templates[name] || templates.Template1;
Ich glaube nicht, dass ich mit require()
so leicht auf einen Standard zurückgreifen kann. Dies führt zu einem Fehler, wenn ich versuche, einen konstruierten Vorlagenpfad zu importieren, der nicht vorhanden ist.
Gute Beispiele und Vergleiche zwischen Anfordern und Import finden Sie hier: http://www.2ality.com/2014/09/es6-modules-final.html
Hervorragende Dokumentation zum Reexport von @iainastacio: http://exploringjs.com/es6/ch_modules.html#sec_all-exporting-styles
Ich bin an Feedback zu diesem Ansatz interessiert :)
Es gibt eine neue Spezifikation, die als dynamic import für ES-Module bezeichnet wird .. _. Im Grunde rufen Sie einfach import('./path/file.js')
und Ihr Guthaben auf. Die Funktion gibt ein Versprechen zurück, das mit dem Modul aufgelöst wird, wenn der Import erfolgreich war.
async function import() {
try {
const module = await import('./path/module.js');
} catch (error) {
console.error('import failed');
}
}
Zu den Anwendungsfällen gehören der route-basierte Import von Komponenten für React, Vue usw. und die Möglichkeit, Lazy-Module zu laden, sobald sie zur Laufzeit benötigt werden.
Hier ist eine Erklärung zu Google Developers .
Laut MDN wird es von jedem aktuellen Chrom-Browser und in Firefox 66 hinter einer Flagge unterstützt.
sie können dazu die Notation ohne ES6 verwenden. Das hat bei mir funktioniert:
let myModule = null;
if (needsToLoadModule) {
myModule = require('my-module').default;
}
Ich mag diese Syntax weniger, aber es funktioniert:
.__ anstatt zu schreiben
import memberName from "path" + "fileName";
// this will not work!, since "path" + "fileName" need to be string literal
verwenden Sie diese Syntax:
let memberName = require("path" + "fileName");
Ich würde es so machen
function load(filePath) {
return () => System.import(`${filePath}.js`);
// Note: Change .js to your file extension
}
let A = load('./utils/' + variableName)
// Now you can use A in your module
Dynamischer Import () (verfügbar in Chrome 63+) erledigt Ihre Arbeit. Hier ist wie:
let variableName = 'test.js';
let utilsPath = './utils/' + variableName;
import(utilsPath).then((module) => { module.something(); });
Ich verstehe die Frage, die speziell für ES6 import
in Node.js gestellt wurde, aber die folgenden Informationen können anderen dabei helfen, eine allgemeinere Lösung zu finden:
let variableName = "es5.js";
const something = require(`./utils/${variableName}`);
Beachten Sie, wenn Sie ein ES6-Modul importieren und auf den default
-Export zugreifen müssen, müssen Sie eine der folgenden Optionen verwenden:
let variableName = "es6.js";
// Assigning
const defaultMethod = require(`./utils/${variableName}`).default;
// Accessing
const something = require(`./utils/${variableName}`);
something.default();
Sie können auch die Destrukturierung mit diesem Ansatz verwenden, wodurch Ihre anderen Importe mit der Syntax vertraut werden:
// Destructuring
const { someMethod } = require(`./utils/${variableName}`);
someMethod();
Wenn Sie auf default
sowie auf die Destrukturierung zugreifen möchten, müssen Sie dies leider in mehreren Schritten durchführen:
// ES6 Syntax
Import defaultMethod, { someMethod } from "const-path.js";
// Destructuring + default assignment
const something = require(`./utils/${variableName}`);
const defaultMethod = something.default;
const { someMethod, someOtherMethod } = something;