| | |
| | | * @returns {string} mode |
| | | */ |
| | | function getMakeDeferredNamespaceModeFromExportsType(exportsType) { |
| | | if (exportsType === "namespace") return `/* ${exportsType} */ 0`; |
| | | if (exportsType === "default-only") return `/* ${exportsType} */ 1`; |
| | | // number is from createFakeNamespaceObject mode ^ 1 |
| | | if (exportsType === "namespace") return `/* ${exportsType} */ 8`; |
| | | if (exportsType === "default-only") return `/* ${exportsType} */ 0`; |
| | | if (exportsType === "default-with-named") return `/* ${exportsType} */ 2`; |
| | | if (exportsType === "dynamic") return `/* ${exportsType} */ 3`; |
| | | return ""; |
| | | if (exportsType === "dynamic") return `/* ${exportsType} */ 6`; |
| | | throw new Error(`Unknown exports type: ${exportsType}`); |
| | | } |
| | | |
| | | /** |
| | |
| | | */ |
| | | constructor(hasAsyncRuntime) { |
| | | super("make optimized deferred namespace object"); |
| | | /** @type {boolean} */ |
| | | this.hasAsyncRuntime = hasAsyncRuntime; |
| | | } |
| | | |
| | | /** |
| | | * Generates runtime code for this runtime module. |
| | | * @returns {string | null} runtime code |
| | | */ |
| | | generate() { |
| | |
| | | // Note: must be a function (not arrow), because this is used in body! |
| | | `${fn} = function(moduleId, mode${hasAsync ? ", asyncDeps" : ""}) {`, |
| | | Template.indent([ |
| | | "// mode: 0 => namespace (esm)", |
| | | "// mode: 1 => default-only (esm strict cjs)", |
| | | "// mode: 2 => default-with-named (esm-cjs compat)", |
| | | "// mode: 3 => dynamic (if exports has __esModule, then esm, otherwise default-with-named)", |
| | | "var r = this;", |
| | | hasAsync ? "var isAsync = asyncDeps && asyncDeps.length;" : "", |
| | | "var obj = {", |
| | |
| | | // if exportsType is "namespace" we can generate the most optimized code, |
| | | // on the second access, we can avoid trigger the getter. |
| | | // we can also do this if exportsType is "dynamic" and there is a "__esModule" property on it. |
| | | 'if(mode == 0 || (mode == 3 && exports.__esModule)) Object.defineProperty(this, "a", { value: exports });', |
| | | 'if(mode & 8 || (mode & 4 && exports.__esModule)) Object.defineProperty(this, "a", { value: exports });', |
| | | "return exports;" |
| | | ]), |
| | | "}" |
| | |
| | | */ |
| | | constructor(hasAsyncRuntime) { |
| | | super("make deferred namespace object"); |
| | | /** @type {boolean} */ |
| | | this.hasAsyncRuntime = hasAsyncRuntime; |
| | | } |
| | | |
| | | /** |
| | | * Generates runtime code for this runtime module. |
| | | * @returns {string | null} runtime code |
| | | */ |
| | | generate() { |
| | |
| | | ? "init?.();" |
| | | : "if (init) init();"; |
| | | return `${fn} = ${runtimeTemplate.basicFunction("moduleId, mode", [ |
| | | "// mode: 0 => namespace (esm)", |
| | | "// mode: 1 => default-only (esm strict cjs)", |
| | | "// mode: 2 => default-with-named (esm-cjs compat)", |
| | | "// mode: 3 => dynamic (if exports has __esModule, then esm, otherwise default-with-named)", |
| | | "", |
| | | "var cachedModule = __webpack_module_cache__[moduleId];", |
| | | "if (cachedModule && cachedModule.error === undefined) {", |
| | | Template.indent([ |
| | |
| | | hasAsync |
| | | ? `if (${RuntimeGlobals.asyncModuleExportSymbol} in exports) exports = exports[${RuntimeGlobals.asyncModuleExportSymbol}];` |
| | | : "", |
| | | "if (mode == 0) return exports;", |
| | | `if (mode == 1) return ${RuntimeGlobals.createFakeNamespaceObject}(exports);`, |
| | | `if (mode == 2) return ${RuntimeGlobals.createFakeNamespaceObject}(exports, 2);`, |
| | | `if (mode == 3) return ${RuntimeGlobals.createFakeNamespaceObject}(exports, 6);` // 2 | 4 |
| | | "if (mode & 8) return exports;", |
| | | `return ${RuntimeGlobals.createFakeNamespaceObject}(exports, mode);` |
| | | ]), |
| | | "}", |
| | | "", |
| | |
| | | ? `if (${RuntimeGlobals.asyncModuleExportSymbol} in ns) ns = ns[${RuntimeGlobals.asyncModuleExportSymbol}];` |
| | | : "", |
| | | "init = null;", |
| | | "if (mode == 0 || mode == 3 && ns.__esModule && typeof ns === 'object') {", |
| | | "if (mode & 8 || mode & 4 && ns.__esModule && typeof ns === 'object') {", |
| | | Template.indent([ |
| | | "delete handler.defineProperty;", |
| | | "delete handler.deleteProperty;", |
| | |
| | | "delete handler.ownKeys;", |
| | | "delete handler.getOwnPropertyDescriptor;" |
| | | ]), |
| | | "} else if (mode == 1) {", |
| | | "} else {", |
| | | Template.indent([ |
| | | `ns = ${RuntimeGlobals.createFakeNamespaceObject}(ns);` |
| | | ]), |
| | | "} else if (mode == 2) {", |
| | | Template.indent([ |
| | | `ns = ${RuntimeGlobals.createFakeNamespaceObject}(ns, 2);` |
| | | ]), |
| | | "} else if (mode == 3) {", |
| | | Template.indent([ |
| | | `ns = ${RuntimeGlobals.createFakeNamespaceObject}(ns, 6);` |
| | | `ns = ${RuntimeGlobals.createFakeNamespaceObject}(ns, mode);` |
| | | ]), |
| | | "}" |
| | | ])};`, |
| | |
| | | `getOwnPropertyDescriptor: ${runtimeTemplate.basicFunction("_, name", [ |
| | | "switch (name) {", |
| | | Template.indent([ |
| | | 'case "__esModule": return { value: true, configurable: !!mode };', |
| | | 'case Symbol.toStringTag: return { value: "Deferred Module", configurable: !!mode };', |
| | | 'case "__esModule": return { value: true, configurable: !(mode & 8) };', |
| | | 'case Symbol.toStringTag: return { value: "Deferred Module", configurable: !(mode & 8) };', |
| | | 'case "then": return undefined;' |
| | | ]), |
| | | "}", |
| | | init, |
| | | "var desc = Reflect.getOwnPropertyDescriptor(ns, name);", |
| | | 'if (mode == 2 && name == "default" && !desc) {', |
| | | 'if (mode & 2 && name == "default" && !desc) {', |
| | | Template.indent("desc = { value: ns, configurable: true };"), |
| | | "}", |
| | | "return desc;" |